In letzter Zeit wurden viele Kopien um technische Interviews gebrochen. Offensichtlich hat das Invertieren eines Binärbaums auf einem Board wenig mit den praktischen Fähigkeiten eines echten Programmierers zu tun. Der primitive
Fizzbuzz ist immer noch der effektivste Test. Infolgedessen hat die Aufmerksamkeit für Open Source-Projekte zugenommen, aber es stellte sich heraus, dass dies
auch kein sehr guter Indikator ist , da die meisten Fachleute keine Zeit für sie haben.
Wir haben heute das effektivste Coding-Interview in unserem Unternehmen - es ist normalerweise eine Art Hausaufgabe für ein paar Tage, in der der Kandidat gebeten wird, einen Fehler zu beheben oder eine kleine Funktion zu implementieren. Dies ist nicht gut, da es lange dauert und die Person Hilfe von außen erhalten kann (oder Google, wenn die Funktion häufig genug ist). Auf der anderen Seite haben einige große Unternehmen stattdessen die Anzahl der Whiteboard-Interviews (und -Algorithmen) verdoppelt und zukünftige Ingenieure stundenlangen Online-Programmiersitzungen mit unterschiedlichem Grad an invasiver Überwachung unterzogen.
Alle diese Interviewtechniken stimmen nicht mit einer sehr einfachen Metrik überein : Factorio zusammen spielen... Das Durchlaufen des gesamten Factorio-Zyklus ist ein nahezu perfekter Indikator dafür, wie gut eine Person in der Lage ist, häufig auftretende technische Probleme zu lösen. Sie können das Durchspielen sogar basierend auf der zukünftigen Position anpassen, um besser zu verstehen, wie der Kandidat mit seiner Rolle umgehen wird.
Factorio?
Factorio ist ein Automatisierungsspiel. Dieser Trailer wird wahrscheinlich die beste Einführung sein , aber im Wesentlichen besteht Ihre Aufgabe darin, eine automatisierte Anlage zu bauen, mit der eine Rakete in den Weltraum abgefeuert werden kann.
Von Anfang an anfangen. Sie bauen Eisenerz und Stein von Hand ab, bauen eine Schmelze, um Erz zu Eisenplatten zu schmelzen, aus denen Sie eine automatische Festbrennstoffbohrmaschine herstellen können. Sie können Eisenerz unabhängig von der Bohrmaschine aufnehmen und in die Schmelze geben. Die Verwendung eines automatischen Förderers ist jedoch effizienter. Dann können Sie das resultierende Eisen verwenden, um einen weiteren Bohrer herzustellen, der den Kohlebergbau automatisiert. Dann wird ein Förderer gebaut, um Kohle zu sammeln, und ein Förderer, um sie auf den Bohrer zu übertragen. Diese winzige Fabrik stellt Eisenplatten her, aus denen ein dritter Bohrer hergestellt werden kann - und beginnt mit dem Abbau von Kupfererz, mit dem Sie Kupferplatten herstellen können. Daraus können Sie Kupferdraht herstellen, der für eine Tauchpumpe erforderlich ist. In Kombination mit einem Dampfkessel und einer Dampfmaschine erhalten wir unseren ersten Strom.Es kann für ein Forschungszentrum und die Erfindung neuer Technologien wie einer Montagemaschine verwendet werden. Sobald Sie die Montagemaschinen entsperrt haben, können Sie mit dem handgefertigten Draht eine Montagemaschine erstellen, die diese Drähte automatisch herstellt.
Am Ende werden Sie Züge, Roboter und Logistiksysteme freischalten, die Ihnen helfen, mit der wachsenden logistischen Komplexität des Spiels umzugehen. Nun, am Ende können Sie eine Rakete in den Weltraum starten.
Wahl der Richtung
Das Spiel beginnt ohne Tor und fast ohne Richtung. Der leitende Programmierer sollte in der Lage sein, die Benutzeroberfläche zu lernen, ein Ziel zu definieren und dann einen Plan zu entwickeln, um es zu erreichen. Vom Junior wird erwartet, dass er die vom Hauptentwickler festgelegten Aufgaben korrekt ausführt. Der Auszubildende soll mit einem Mentor zusammenarbeiten, aber der Junior sollte in der Lage sein, zugrunde liegende Probleme mit seinem Code selbst zu beheben, bevor er den Senior um Hilfe bittet. Middle muss in der Lage sein, selbständig zu arbeiten, sobald er einen Auftrag erhält, aber von ihm wird nicht erwartet, dass er architektonische Entwürfe macht.
Spezifische Erwartungen können wie folgt formuliert werden:
- Der Auszubildende muss normalerweise in der Lage sein, eine Blaupause zu platzieren und sie mit etwas anderem zu verbinden, beispielsweise einer Erzlagerstätte.
- , . , .
- , ( ) .
- , , .
Der wichtigste Aspekt der Softwareentwicklung ist die Teamarbeit. Dies bedeutet, dass Sie sich mit anderen Personen abstimmen, die Anforderungen der Projekte anderer Personen erfüllen und mit dem Team zusammenarbeiten müssen, anstatt selbstständig zu arbeiten, wenn Sie sich weigern, Ihr Design zu ändern, um die Integration in die Arbeit anderer Personen zu unterstützen. Natürlich treten solche Situationen in Factorio immer wieder auf, da Standardpläne auf den physischen Raum beschränkt sind. Infolgedessen müssen Sie die Aktionen anderer Personen sorgfältig untersuchen und manchmal Ihr Design so anpassen, dass es innerhalb der Größenbeschränkungen liegt, oder sich an die Zeichnung anderer Personen anpassen, die mehr Platz beansprucht als erwartet.
Wenn sich der Spieler in sich zurückzieht, anfängt, alles selbst zu tun oder Probleme stillschweigend behebt, wird dies schnell den Zorn des Teams auf sich ziehen, aus den gleichen Gründen, aus denen Kollegen auf Cowboy-Programmierer verärgert sind. Glücklicherweise hat Factorio ein eingebautes Äquivalent
git blame
: Es zeigt den letzten Spieler, der eine Entität geändert hat. Wenn also jemand eine Krücke anlegt und das Team nicht über das Problem informiert, dann weiß jeder, wer schuld ist, wenn diese Krücke schließlich bricht. Wenn Sie gewinnen wollen, müssen Sie eng mit Ihren Teamkollegen zusammenarbeiten.
Debuggen
Das Debuggen ist eine der Hauptfähigkeiten eines Programmierers. Dies ist vielleicht die offensichtlichste Parallele zwischen Factorio und der tatsächlichen Softwareentwicklung. Etwas kann sehr weit von der eigentlichen Ursache des Problems entfernt sein. Die Fähigkeit, ein echtes Problem schnell herauszufinden, ist eine entscheidende Fähigkeit, und der Denkprozess ist fast identisch mit dem Aufspüren der Ursache eines echten Programmfehlers. Wenn der Picker nicht mehr funktioniert, müssen Sie zuerst die ausgehenden Flows überprüfen. Überprüfen Sie dann, welche Zutat am Eingang fehlt. Verfolgen Sie dann die Zutat durch die Fabrik, um herauszufinden, wo sie hergestellt wird. Und wiederholen Sie den Vorgang immer und immer wieder, bis Übelkeit.
Das Debuggen in Factorio wird schnell kompliziert. Sobald Sie eine Ölraffinerie bauen, werden Sie mit dem Cracken beginnen, wo sich am Ausgang drei verschiedene Rohre befinden (Heizöl, Dieselkraftstoff und zugehöriges Erdölgas), und wenn eines davon aus irgendeinem Grund ins Stocken gerät, dann die gesamte Raffinerie hört auf zu arbeiten.
Es gab Zeiten, in denen die gesamte Anlage stehen blieb, weil Sie angefangen haben, etwas zu erforschen, für das keine gelbe Wissenschaft erforderlich war. Infolgedessen haben Sie die Verwendung von Drohnenrahmen eingestellt, die nicht mehr mit Elektromotoren geliefert wurden, für deren Herstellung Heizöl verwendet wurde. Infolgedessen kam das Auslassrohr in der Raffinerie zum Stillstand, was dazu führte, dass Ihnen das zugehörige Erdölgas (Benzin) ausgeht, wodurch die Produktion von Kunststoff gestoppt wurde. Infolgedessen wurde die Produktion des roten Signaldrahtes eingestellt - und die gesamte Fabrik war außer Betrieb. Erfahrene Spieler antizipieren solche Szenarien und implementieren selbstausgleichende Ölcracking, um sicherzustellen, dass das System immer ausgeglichen ist. Eine solche Anlage stoppt nur, wenn das Auslassrohr mit dem zugehörigen Gas verstopft ist.Wenn ein guter Programmierer eine kaputte Raffinerie erhält, kann er das Problem normalerweise bis zur Quelle zurückverfolgen, verstehen, was passiert ist, und schnell versuchen, eine Lösung zu finden. Auf der anderen Seite, wenn eine Person ohne guten Grund nur ein paar neue Tanks auf den Boden wirft (sie ist absolut sicher, dass das Schmiermittel immer benötigt wird), dann ist dies eine große rote Fahne für die Methoden zur Lösung von Problemen in seine Programme.
In solchen Situationen kann Factorio die komplexen Abhängigkeiten, mit denen Programmierer normalerweise umgehen, genau nachahmen. Der Schwierigkeitsgrad steigt, wenn dem Gameplay neue Konzepte hinzugefügt werden. Dies ist sehr ähnlich zu der zunehmenden Komplexität durch zusätzliche Abstraktionsebenen beim Debuggen eines Absturzes, der tief in einem der von Ihnen verwendeten Frameworks aufgetreten sein könnte.
Code-Review
Oft muss das ursprüngliche Design angepasst werden, um die Leistung oder den Durchsatz zu verbessern. Gute Programmierer werden Kritik an ihren Entwürfen nicht nur akzeptieren, sondern auch in zukünftigen Arbeiten berücksichtigen. Wenn sie mit der Änderung nicht einverstanden sind, geben sie eine spezifische Erklärung ab, damit das Team die Vor- und Nachteile der vorgeschlagenen Änderung genauer reflektieren kann.
Sich ohne guten Grund dem Feedback zu widersetzen, ist eine bekannte rote Fahne. Darüber hinaus ist der Programmierer, der die vorgeschlagenen Änderungen nur ungern akzeptiert und sich weigert, zukünftige Projekte entsprechend anzupassen, vorsichtig. Infolgedessen muss er ständig an die Notwendigkeit erinnert werden, sich an eine Standardmethode zur Lösung des Problems zu halten. Gleichzeitig erklärt die Person nicht, warum sie die vorgeschlagene Methode nicht mag. Dies ist möglicherweise eine tickende Zeitbombe für ein Unternehmen, da er unbeaufsichtigt schnell technische Schulden für seine Kollegen ansammeln kann. Solche Probleme sind in einem traditionellen Interview nur während eines Praktikums kaum zu erfassen.
Codierungsstil und Frameworks
Die Nichtbeachtung von Ratschlägen ist nur ein Teil eines viel größeren Problems, wenn der Programmierer nicht in der Lage ist, sich ordnungsgemäß in die vorhandene Struktur zu integrieren. Es gibt viele Möglichkeiten, eine Fabrik in Factorio zu erstellen, und jede erfordert Standard-Erstellungsmethoden. Die Nichteinhaltung von Standards wird die gesamte Fabrik schnell zum Stillstand bringen, oft auf subtile Weise, die für den unachtsamen Entwickler nicht offensichtlich sind.
Das Design des Hauptbandförderers umfasst 4-8 Förderer, die in zwei Abschnitte unterteilt sind (für unterirdische Förderer). Es befindet sich in der Mitte der Fabrik und die gesamte Produktion erfolgt senkrecht zum Band. Dieses Design basiert auf mehreren Regeln, deren Verletzung zu völligem Chaos führen kann. Zunächst sollten Sie immer einen Abscheider am Ausgang des Förderers verwenden. Sie sollten niemals ein ganzes Band umleiten: Leerer Speicherplatz für ein anderes Band bedeutet, dass Sie auch nach einem Upgrade eine ganze Pipeline von Ressourcen verlieren. Zweitens müssen alle Fabriken senkrecht zum Hauptförderer skalieren. Wenn Sie nicht schnell skalieren, wird entweder viel Platz verschwendet oder die Produktionslinie kann nicht skaliert werden, da sie von anderen Produktionslinien umgeben ist.
Logistiknetzwerk
Es gibt verschiedene Möglichkeiten, Logistiknetzwerke aufzubauen. Am einfachsten ist es mit passiven Versorgungskisten. Es gibt aber noch eine andere Methode - Filterkisten, die das Müllproblem lösen. Beide Methoden erfordern die korrekte Platzierung der Rückhaltesysteme an den richtigen Stellen. Passive Versorgungskisten sind normalerweise durch den Brustraum begrenzt. Sie müssen einen Manipulator an den Lagerkisten anbringen, um die Truhe mit dem Logistiknetzwerk zu verbinden. Stellen Sie mindestens N Elemente bereit, bevor Sie den Manipulator installieren. Wenn Sie diese Schritte vergessen, werden enorme Ressourcen verschwendet. Wenn ein Programmierer die Leistungsbegrenzer ständig vergisst, ist dies eine rote Fahne, dass eine Person die Leistung in realen Anwendungen nicht berücksichtigt.
In anderen Fällen kann das Team vorgefertigte Baupläne verwenden, z. B. ein Kernreaktordesign oder eine Roboterdrohnenfabrik (Botfabrik). Sie können extrem schwierig sein, aber wenn Sie sich anstrengen und es herausfinden, sind sie extrem zeitsparend. Hüten Sie sich vor Kandidaten, die ein neues Element in der Fabrik nicht anpassen möchten, nur weil sie keine komplexe Steuerlogik verfolgen können. Oder wer gibt es auf, den Algorithmus für die Funktionsweise einer solchen Anlage herauszufinden, trotz der offensichtlichen Vorteile von Drohnen gegenüber Förderbändern. Suboptimales Drohnenanlagen-Design, Quelle
Multithreading
Züge in Factorio sind ein direktes Analogon zum Multithreading: Ein Zug ist ein Ausführungsthread, und jede Zugkreuzung oder Haltestelle ist ein Ort im Speicher, an dem möglicherweise zwei Threads gleichzeitig schreiben können. Ampeln sind Schlösser (oder Mutexe). Alle Fehler im Eisenbahnnetz manifestieren sich auf die gleiche Weise wie die Rennbedingungen in der Software, da sie buchstäblich die physischen Rennbedingungen sind. Auch hier gelten alle Kompromisse - zu langes Blockieren verringert den Durchsatz. Ein unsachgemäßes Design von Ampeln führt normalerweise zu Deadlocks, genau wie bei Software, da das Endergebnis eine zyklische Interlocking-Abhängigkeit ist. Der häufigste Stillstand ist, wenn ein Zug zu lang ist und unerwartet eine zweite Kreuzung blockiert, während er auf die Einfahrt in die erste wartet.Diese zweite Kreuzung verhindert dann, dass ein anderer Zug abfährt, und verhindert, dass die erste Kreuzung entsperrt wird.
Die Anzahl der Gleise im Schienennetz entspricht der Anzahl der CPU-Kerne. Es ist schwierig, eine einzelne Spur auf mehr als einige Spuren zu skalieren, da die Kapazität des gesamten Systems selbst in Wartebereichen sehr schnell begrenzt ist. Das gebräuchlichste Design ist ein zweispuriges Design mit einer Spur auf jeder Seite. Hier treten Kapazitätsprobleme auf, wenn ständig Züge entladen werden müssen. Daher haben große Schienennetze mindestens vier Fahrspuren, wobei die beiden äußeren als Umgehungsgleise dienen, um Kreuzungen nach Möglichkeit zu vermeiden.
Ampelprobleme in diesen Systemen können sich in fantastischer Zeit manifestieren. Eine einzelne verpasste Ampel im selben Schienennetz verursachte nach zweiwöchiger ordnungsgemäßer Arbeit einmal einen Stillstand . Ebenso kann in Programmen die Race-Bedingung nur einmal im Monat auftreten, wenn unter hoher Last eine hohe Parallelität von Threads auftritt.
Skalierung
Wie bei der Software stellt die Produktionsskalierung von Factorio das ursprüngliche Blaupausen-Design vor neue Herausforderungen und erfordert häufig eine vollständige Überarbeitung, um die Produktivität zu maximieren. Dabei werden Produktivitätsmodule und Geschwindigkeitsmodule mit Beacons installiert. Förderer werden selbst bei maximaler Bandgeschwindigkeit zu einem Leistungsengpass, wodurch Möglichkeiten erzwungen werden, Strukturen zu teilen, damit später mehr Bänder eingesetzt werden können, oder Fabriken in Module zu unterteilen.
Die Verwaltung des Logistiknetzwerks selbst wird am Ende des Spiels aufgrund der Anzahl der Probleme, die durch ausgedehnte Drohnen-Netzwerke verursacht werden, zu einer logistischen Herausforderung. In der Regel müssen Sie mit der Segmentierung der Lieferkette beginnen und entweder Züge verwenden, um Waren zwischen Segmenten zu transportieren, oder Anforderungs- und Lieferkisten erstellen, die Waren grenzüberschreitend transportieren.
Am Ende des Spiels erfordert das Zugmanagement einen Wechsel von der Push-Architektur zur Pull-Architektur, da die Push-Architektur keine hohe Bandbreite bewältigen kann. Dies führt unweigerlich zur Verwendung der Train Limit-Funktion und zum Erlernen der Verwendung logischer Netzwerke zum Codieren der Grundlogik, sodass der Bahnhof einen Zug nur dann anfordert, wenn er wirklich bereit ist, ihn vollständig mit Ressourcen zu füllen, anstatt der üblichen Spieltaktik bei Der Beginn des Spiels, wenn ein paar Züge einfach den Befehl erhalten, Eisen zu holen. Das neue System minimiert die Anzahl der Züge und stellt gleichzeitig sicher, dass alle Stationen im Netz bedient werden.
Es kommt häufig vor, dass die Einschränkungen der Eingangsleitungen zur Montagemaschine und die Geschwindigkeitsbegrenzungen des Manipulators eine Neugestaltung der Fabriken erfordern, ebenso wie das Hochgeschwindigkeits-Computing die Kenntnis der Engpässe in der CPU erfordert. Diese Engpässe sind fast nie ein Problem, bis Sie eine bestimmte Skala erreicht haben, aber danach beginnen sie, die Leistung einzuschränken.
Microservices und Module
Schließlich werden Fabriken so groß, dass sie ein einfaches Design mit einem Hauptförderband- oder Spaghetti-Design aufgeben und zu einer skalierbareren Struktur übergehen müssen. Um das Mega-Level zu erreichen, verwenden Fabriken normalerweise entweder ein Zugsystem oder ein modulares System, das in etwa den Microservices oder der Plug-In-Architektur entspricht.
Die zugbasierte Mega-Basis wird manchmal als "Stadtblock" -Design bezeichnet, bei dem Züge um die Werksblöcke alle Ein- und Ausgänge steuern. Auf diese Weise wird jeder einzelne Block von allen anderen isoliert, da alle Eingänge in dem Sinne "sauber" sind, dass sie aus dem Schienennetz stammen. Dies ist nahezu identisch mit der Architektur von Mikrodiensten (über HTTP) oder Interprozesskommunikation (IPC) mit ähnlichen potenziellen Problemen aufgrund von E / A-Verzögerungen, da Ergebnisse nicht immer empfangen werden können und in "Paketen" gesendet werden müssen. oder Züge über das Schienennetz.
Die modulare Architektur versucht, einen gewissen Anschein des Hauptförderers aufrechtzuerhalten, trennt jedoch stattdessen die Bänder im Werk und verwendet modulare Blöcke, die Standardeingaben und Standardeingaben akzeptieren. Manchmal kann dies vollständig mit Drohnen erreicht werden, aber normalerweise müssen Materialien über große Entfernungen mit einem Förderband transportiert werden. Dies ist dem Modulsystem für eine monolithische Anwendung mit den gleichen Kompromissen sehr ähnlich.
Diese Megabasen stellen die oberste Ebene des Standard-Factorio-Servers dar. Natürlich gibt es viele Mods, die das Spiel viel schwieriger machen.
Verteilte Systeme
Space Exploration ist eine komplett überarbeitete Version von Factorio für die Besiedlung des Weltraums. Hier werden Planeten ressourcenbeschränkt, und die Spieler müssen andere Welten kolonisieren und Raketen einsetzen, um Ressourcen zwischen Planeten zu übertragen. Aufgrund der enormen Verzögerung bei der Lieferung von Material zwischen Planeten führt die Koordination dieser Basen zu Problemen, die einem global verteilten Datenbanksystem ähneln. Selbst im logischen Netzwerk müssen Sie mit der Latenz kämpfen, da das automatische System die Elemente aus den Augen verliert, die gestartet werden, aber den Zielplaneten noch nicht erreicht haben. Wenn dies nicht berücksichtigt wird, gibt es doppelte Abfragen für alle erforderlichen Elemente. Verteilte Systeme haben genau das gleiche Problem, wenn sie versuchen, die Konsistenz zwischen Knoten sicherzustellen.
Ausgabe
Im Allgemeinen hat die Softwareindustrie keine Ahnung, wie die besten Entwickler gefunden und eingestellt werden können. Wahrscheinlich war es das beste technische Interview, das wir je gemacht haben, Factorio zusammen zu spielen. Und das verwirrt uns sehr . Dieses Interview ist äußerst unpraktisch und dauert beim ersten Mal mehr als 20 Stunden im Mehrspielermodus oder 8 Stunden für ein Team erfahrener Spieler. Was kann man daraus lernen? Weiß nicht. Wir können sicherlich nicht zu Factorio als Interviewmethode wechseln - genauso gut geben Sie dem Kandidaten Hausaufgaben.
Aber das ist besser als ein Whiteboard-Interview.