Was tun, wenn Sie alle Möglichkeiten zur Behebung eines Fehlers ausgeschöpft haben?


13

Ich bin ein Junior-Programmierer (4 Monate Berufserfahrung) und arbeite an einer plattformübergreifenden mobilen Anwendung (1-Personen-Team - also bin ich alleine).

Ich habe einen Fehler in diesem Programm / dieser App, der ziemlich groß ist (30 verschiedene Header-Dateien, jede mit einer eigenen CPP-Datei). Ich habe versucht, genau herauszufinden, was mit dem Fehler los ist und auch, um ihn zu beheben (ich habe sogar versucht, einige Hacks zu verwenden, um ihn zum Laufen zu bringen), aber ich habe ungefähr ein Dutzend oder mehr Lösungen (Ideen, was das Problem verursacht) ) Ich habe nichts gefunden, was mich dazu gebracht hat, genau zu verfolgen, was der Fehler ist oder den Fehler zu beheben.

Haben Sie einen Rat für einen Junior-Programmierer, der einige allgemeine Techniken beherrscht (probieren Sie es aus, drucken Sie meinen gesamten Code auf Papier und gehen Sie ihn mit einem Stift durch usw.), den ich verwenden könnte, um mir bei diesem Fehler zu helfen?

Um meinem Bug etwas mehr Kontext zu geben; Es handelt sich um die plattformübergreifende API Mosync. Wenn ich eine bestimmte Abfolge von Aktionen durchführe, wird auf dem aktuellen Bildschirm nicht neu gezeichnet (und es wird angezeigt), dass der zuvor angezeigte Bildschirm weiterhin die Zeiger- / Tastendruckereignisse und nicht den aktuellen Bildschirm empfängt.

Bestimmte Reihenfolge:
- Angezeigter Menübildschirm - Klicken Sie auf die Schaltfläche "
Vorherige Bestellungen anzeigen " - Angezeigter Bildschirm "Vorherige Bestellungen" - Klicken Sie auf "Datei laden" und dann auf die Menüschaltfläche und öffnen Sie den Lieferungsbildschirm
- Angezeigter Lieferungsbildschirm - Klicken Sie auf die Menüschaltfläche und öffnen Sie den Kaufbildschirm
- Angezeigter Kaufbildschirm - Fehler hier, Eingabe in diesen Bildschirm wird nicht angezeigt / reagiert, ListViews scrollen nicht, Schaltflächen reagieren nicht auf Klicks, ListView-Zellen reagieren nicht auf Klicks


Ich werde den Rat an Bord nehmen, der Fehler ist jedes Mal zu 100% reproduzierbar, wenn man die gleichen Schritte befolgt, obwohl es immer noch sehr schwierig ist herauszufinden, wie Zeigerereignisse übertragen werden und auf welchen Bildschirm, da dies ein Teil der API ist, den ich nicht kann erreichen (oder nicht wissen wie).

Ich würde auch gerne ein anderes Paar Augen haben, das meine Arbeit überprüft und auf den Fehler hinweist, aber wie gesagt, ich bin ein 1-köpfiges Team, mein Chef leitet mich, er besitzt die Firma und hat die Ideen für eine App, tut dies aber Ich kenne weder C ++ noch eine neuere Sprache (Cobal? Ich denke ist alles). Irgendwelche Ratschläge, wie man ein zweites Paar Augen bekommt, ohne den intellektuellen Code / das geistige Eigentum des Unternehmens zu verletzen / vorzuführen?

... und kein Verlassen dieses bezahlten Praktikums ist keine Option. Wenn ich vor 6 Monaten eines 12-Monats-Vertrages verlasse, muss ich möglicherweise 30% meines Jahresgehalts zahlen


6
Ist es zu 100% reproduzierbar?

5
Die einfache Antwort ist , Ihre Kollegen einzubeziehen . Als Team werden Sie es in wenigen Augenblicken lösen.
Fattie

2
@ Joe - nicht immer. Zum Beispiel Fehler im kollektiven Verhalten mehrerer komplexer interagierender Subsysteme, bei denen verschiedene Subsysteme mit subtil inkompatiblen Ansichten ihrer Rollen erstellt wurden, die auf nicht offensichtlichen Unklarheiten in den Spezifikationen beruhen - in der Regel verfügen nur sehr wenige Personen über detaillierte Kenntnisse über mehrere Subsysteme und deren Interaktionen in der Lage sein, diese Probleme zu diagnostizieren. Manchmal muss man alle Teams zum Reden bringen, und wenn zwei Leute anfangen, sich gegenseitig als Idioten zu bezeichnen, besteht die Möglichkeit, dass sie etwas diskutieren, das in Zusammenhang mit den inkompatiblen Annahmen steht.
Steve314

Ich habe deine Konten zusammengeführt. Sie können sich mit Ihrer Yahoo OpenID anmelden. Ich bearbeite Ihre Frage auch so, dass die von Ihnen geposteten Informationen als Antwort angezeigt werden.
Adam Lear

btw. Zusätzlich zu meiner Antwort unten habe ich auf Wikipedia gelesen, dass Mosync nicht mehr gewartet wird.
Brad Thomas

Antworten:


19

Wenn Sie das Problem in 100% der Fälle reproduzieren können, legen Sie im letzten Schritt einen Haltepunkt fest (so früh wie möglich). Wenn Sie den gesamten Aufrufstapel durchgehen, sind Sie sich ziemlich sicher, dass Sie irgendwo auf unerwartete Werte stoßen oder auf Werte, die aufgerufen werden sollten, aber nicht.

Bearbeiten:

Und wenn Sie am Ende Ihres Witzes sitzen und versuchen, den Fehler zu beheben und hier etwas zu posten, in der Hoffnung, dass Sie einen Ratschlag mit strahlendem Licht erhalten, gehen Sie weg . Mach deinen Kopf frei und komm später wieder (am besten morgen oder nach dem Wochenende). Es gab so manche Zeit, in der ich einen ganzen Tag nach einer Lösung für ein bestimmtes Problem gesucht habe, nur um wegzugehen, am nächsten Tag mit klarem Kopf zurückzukehren und es innerhalb von zehn Minuten zu finden.


4
Und wenn Sie aus irgendeinem Grund keinen Debugger verwenden können, geben Sie dem fehlgeschlagenen Codebit, der Ihre Funktionsaufrufe in einer Textdatei protokolliert, Ablaufverfolgungsinformationen.

3
+1 für "Geh weg". Es erfordert viel Erfahrung, um zu wissen, ob das Weggehen möglicherweise produktiver ist, als das Problem zu lösen. Ihre Situation scheint ein guter Ort zu sein, um diese spezifische Erfahrung zu sammeln.
Mike Sherrill 'Cat Recall'

Wenn Ihre Software einen Haltepunkt benötigt, um den Fehler zu erkennen, benötigt auch Ihr Gehirn diesen. Das spart mehr Zeit als sich selbst zu zwingen und nicht wegzulaufen.
Setzamora

Ich habe festgestellt, dass Protokollierungsfunktionen, die möglicherweise relevante Werte protokollieren, häufig eine bessere Möglichkeit sind, solche Vorgänge nachzuverfolgen. Formatieren Sie die Protokollzeilen mit ordentlichen Spalten, damit alle Änderungen für Ihr Auge auffallen. Rufen Sie diese Protokollierungsfunktion häufig mit der ID auf, von der aus sie aufgerufen wird. Sie können die Protokolldatei viel schneller untersuchen, als Sie die Variablen schrittweise überwachen können.
Loren Pechtel

10

Beim Debuggen geht es mehr darum, das Problem genau zu lokalisieren und zu verstehen (im Vergleich zum Anwenden eines Fixes)

Eine Sache, die Sie beim Debuggen beachten sollten, ist, wenn Sie feststellen, dass Sie verschiedenen Theorien folgen, da dies oft länger dauert und mögliche Probleme nicht systematisch beseitigt.

Normalerweise ist der beste Weg, um diese Art von Situationen zu debuggen, der langweilige systematische Ansatz, bei dem Sie Ihr System in kleine Teile aufteilen und jedes Teil für sich arbeiten lassen und jedes Element der Komplexität einzeln hinzufügen, bis es kaputt geht. Dann haben Sie das genaue Problem isoliert. Dieser Weg mag ein wenig langwierig und ein wenig umständlicher erscheinen, entfernt jedoch Variablen und sorgt dafür, dass Ihr Gehirn gesund bleibt, während Sie versuchen, ein komplexes Stück Software zu debuggen.


5

Dies sind nur einige Dinge, die ich in der Vergangenheit getan habe, offensichtlich funktionieren sie nicht in jeder Situation:

  1. Erkennen , dass es nur Code ist, und dort irgendwo ein Fehler ist (es ist nicht nur schwarze Magie) , dass Sie CAN beheben.
  2. Machen Sie eine Pause.
  3. Gehen Sie den Code sehr langsam durch, analysieren Sie jeden Schritt und stellen Sie sicher, dass Sie ihn verstehen und wissen, was er tut, ohne etwas zu beschönigen.
  4. Holen Sie sich ein zweites Paar Augen, um das Problem zu untersuchen.
  5. Geh schlafen und vergiss es bis morgen (mach deinen Kopf frei), komm mit einer neuen Perspektive.
  6. Drucken Sie Ihren Code aus und analysieren Sie jede Zeile. Machen Sie sich Notizen am Rand und verstehen Sie alle Auswirkungen jeder Zeile
  7. Wenn es sich nicht um einen kritischen Fehler handelt, der jedoch Fehler verursacht, über die der Benutzer nichts wissen muss, habe ich den Fehler (beschämt, aber ehrlich) abgefangen und ihn verschluckt ! Wenn es nicht gefährlich ist und Sie die Ursache nicht finden können, fangen Sie manchmal einfach danach und lassen den Benutzer nicht wissen, dass etwas passiert ist. Für den Kunden dreht sich alles um den ROI, und manchmal lohnt es sich nicht.
  8. Sagen Sie dem Bug verbal, dass Sie ihn jagen und töten werden. Manchmal rennt es weg. :-)

+1, denn es ist keine schwarze Magie!
Guy Sirton

Bei all den komplexen Abhängigkeiten, die wir heute in unserem Code berücksichtigen, ist es schwarze Magie. Aber du kannst es gut machen :)
Subu Sankara Subramanian

3

Ich habe normalerweise diesen Ansatz beim Lösen von Fehlern.

  1. Erstellen Sie einen schönen Schritt für Schritt, um den Fehler zu reproduzieren
  2. Vereinfachen Sie die Schritt für Schritt
  3. Wo im Code tritt der Fehler auf? Wie ist es mit welchen Funktionen?
  4. Welchen Pfad wählt der Code, wenn der Fehler auftritt, die Callchain.
  5. Konzentrieren Sie sich auf den Ort, wann ist es in Ordnung, wann nicht. Wiederholen Sie dies so oft, bis Sie genau die Stelle gefunden haben, an der der Fehler aufgetreten ist.
  6. Warum passiert das?

An diesem Punkt ist normalerweise ziemlich klar, was passiert ist, da ich so viel gelernt habe, während ich mich auf das Problem konzentriere, damit ich weiß, was zu tun ist. Oder ich habe eine ziemlich konzentrierte Frage, die ich in einem Forum stellen kann.

Anschließend versuche ich, das Problem zu beheben, und überprüfe anhand der in Schritt 1 erstellten Schritte, ob der Fehler behoben ist.


3

Alle vorherigen Ratschläge sind hervorragend, und ein Großteil davon zielt darauf ab, Vermutungen über den Fehler zu überprüfen und anschließend einen Fehlerbehebungsprozess durchzuführen, um den Fehler zu lokalisieren (manchmal durch Untersuchen der Umgebung um den Fehler herum und manchmal direkt im Code).

Dieser Ansatz funktioniert nicht immer, unabhängig von Ihrem Dienstalter oder Ihrer Fachkenntnis. Manchmal braucht man nur ein paar Augen für das Problem. Suchen Sie jemanden, der das Problem oder die Debugging-Sitzung mit Ihnen bespricht. Wenn Sie häufig nur den Code durchgehen, werden Sie zum Fehler geführt.


Ich stimme zu, das hat bei mir schon oft geklappt.
Mike Dunlavey

1

Wie andere sagten: 1) Sie können es zuverlässig reproduzieren und 2) Sie können in einem Debugger bis zu dem Punkt vorwärts gehen, an dem es passiert.

Wenn ich das aus irgendeinem Grund nicht kann, habe ich zwei andere Methoden, die beide eine andere Version des Codes erfordern, die den Fehler nicht aufweist.

  1. Führen Sie beide Versionen des Codes nebeneinander unter Debuggern aus. Schritt sie entlang, bis der Böse etwas anderes als das Gute tut.

  2. Führen Sie abwechselnd die gute und die schlechte Version des Codes aus. Haben Sie einen diff oder eine andere Liste der Unterschiede zwischen den Versionen. Ändern Sie dann inkrementell den Code einer der beiden Versionen, damit er besser mit der anderen übereinstimmt. Wenn das Böse gut oder das Gute schlecht wird, mache ich eine kleinere Änderung. Auf diese Weise bin ich auf dem Laufenden. Ich betrachte es als "sich auf beiden Seiten des Problems zu bewegen und auf das Zentrum hinzuarbeiten". Diese Methode erfordert keinen Debugger.

Wenn das Problem schwer zu reproduzieren ist, dann muss ich so viele Informationen wie ich bekommen kann, wie zum Beispiel ein Stapelabbild, wenn es nicht passieren. Also stelle ich sicher, dass ich diese Diagnosen bekommen kann, warte auf das Auftreten des Problems und hoffe, dass ich genug Informationen habe, um es zu finden.


1

Wenn Sie als Junior-Programmierer mit der Arbeit beauftragt wurden, gibt es mindestens eine Person, die glaubt, dass Sie in der Lage sind, alles selbst zu handhaben.

Bevor Sie Ihre Vorgesetzten um Hilfe bitten, notieren Sie sich auf einem Zettel die Schritte / Methoden, die Sie beim Aufspüren des Fehlers unternommen haben, wie weit Sie damit gegangen sind, warum Sie die einzelnen Methoden aufgegeben haben und was Sie gelernt haben bei jedem versuch. Fassen Sie außerdem zusammen, was Sie bisher über das Projekt gelernt haben.

Wenn Sie mit dem Aufschreiben fertig sind, sollte das, was getan werden kann, offensichtlich werden. Wenn dies der Fall ist, müssen Sie einfach dem folgen, was sich gezeigt hat, um den Fehler zu reproduzieren, und versuchen Sie, ihn zu beheben. Ist dies nicht der Fall, verfügen Sie über eine Grundlage, auf der Sie mit Ihren Vorgesetzten sprechen können. Wenn Sie um ihre Hilfe bitten, ohne zu zeigen, was Sie getan haben, können sie einen negativen Eindruck auf Sie bekommen.

Aber wenn Sie Ihren Kopf aufräumen und nach dem Wochenende wiederkommen, können Sie es möglicherweise in kürzester Zeit lösen, ohne dass jemand hilft. Es passiert ständig.


"Wenn Sie als Junior-Programmierer mit der Arbeit beauftragt wurden, gibt es mindestens eine Person, die glaubt, dass Sie in der Lage sind, alles selbst zu erledigen." Wenn ich arbeite, wird von allen Entwicklern erwartet, dass sie um Hilfe bitten, wenn sie nach ihrer Hausarbeit keine Lösung haben. Das nennt man Teamarbeit.
Mattnz

@mattnz Ich schlage nur vor, dass Sie, bevor Sie um Hilfe bitten, die bisherigen Bemühungen dokumentieren und sicherstellen, dass alle bekannten Optionen ausgeschöpft sind. Ich weiß nicht, wie ich das nennen soll, aber ich habe nie bestritten, was Sie unter Teamarbeit verstehen.
vpit3833

Ich wollte darauf hinweisen, dass "... in der Lage ist, alles selbst zu handhaben", was bedeutet, dass Sie allein sind. Ich bin froh zu wissen, dass ich es etwas stärker interpretiert habe, als Sie es beabsichtigt hatten.
Mattnz

0

Wir müssen wissen, wie schwierig es ist, sich zu reproduzieren, da die Methode ganz anders ist. Automatisieren Sie die Fehlerursache für einen zuverlässig reproduzierten Fehler. Verwenden Sie Debugger und Debug-Traces (Traces wirken sich am wenigsten auf Fehler vom Typ Race Condition aus). Holen Sie sich methodisch. Schritt für Schritt liefert jeder Schritt weitere Informationen, auch wenn dies die Bestätigung dessen ist, was Sie bereits wissen. Wenn Sie ein überraschendes Ergebnis erhalten, hören Sie auf, es zu 100% zu verstehen, bevor Sie fortfahren. Es ist schmerzhaft langsam, bringt Sie aber immer zum Endergebnis, wenn Sie ihm genügend Zeit geben.

Wenn Sie es nicht ändern können, haben Sie ein Problem. Wie können Sie bestätigen, dass Sie es behoben haben? Geben Sie den Debug-Code ein und lassen Sie ihn dort. Fragen Sie sich schließlich, ob "Geschlossen: DNR" eine gültige Option ist. (Hat / Konnte nicht neu ordnen). Im Geschäftsleben ist es letztendlich eine Kosten-Nutzen-Entscheidung.

Gehen Sie nicht davon aus, dass Ihre Bibliotheken korrekt sind, sondern bestätigen Sie dies.

Machen Sie eine Pause, seien Sie pragmatisch in Bezug auf die Kosten und die Notwendigkeit, sie zu beheben, und bitten Sie vor allem jemanden, sich neben Sie zu setzen und zu helfen.


0

Viele gute Antworten hier. Ein paar andere Tipps:

UIs leben selten isoliert. Erstellen Sie ein Testprogramm mit den minimalen Funktionen, die zum Reproduzieren des Fehlers erforderlich sind. Wenn die Benutzeroberfläche gut konzipiert ist, sollten Sie in der Lage sein, die fehlerhaften Benutzeroberflächenkomponenten zu entkoppeln und sie in einem Testprogramm isoliert auszuführen. Können Sie das Problem noch reproduzieren? In diesem Fall liegt das Problem wahrscheinlich in Ihrer Benutzeroberflächenstruktur oder Ihrem Framework. Überprüfen Sie Ihre UI-Struktur - achten Sie insbesondere auf unsichtbare Elemente. Versuchen Sie genau zu erfahren, was passiert, wenn Sie auf diese ListView klicken und diese nicht reagiert. Welche Event-Handler werden aufgerufen? Bedenken Sie, dass es möglicherweise Fehler im UI-Framework selbst gibt - springen Sie nicht zu dieser Schlussfolgerung, schließen Sie sie jedoch nicht direkt aus. Ein schneller Test besteht darin, Ihre Mosync-Version zu aktualisieren und zu überprüfen, ob die Symptome nicht mehr auftreten.

Gelingt das nicht: Was bleibt in Ihrem Testprogramm? Verstehen Sie alle verbleibenden Komponenten, insbesondere alle laufenden Threads. Etwas, das Datenbankwartung im Hintergrund erledigt? Ein Datei-Spooler? Überwachungscode für NSA-Benutzerverhalten? Funktioniert die Benutzeroberfläche mit einigen dieser Komponenten (möglicherweise im Hintergrund)? Von welchen Hintergrundoperationen hängt die Benutzeroberfläche ab?

Achten Sie beim Lesen des Codes, für den Sie aufgrund der Schwierigkeit des Fehlers viel Zeit aufwenden sollten, auf einige schlechte Vorgehensweisen, die Ihren Fehler verdecken könnten. Sehen Sie etwas davon?

try {
    SaveTheWorld();
} catch (std::exception& ex) { /* oh it didn't work, let's just ignore it */ }

Das ist eine unglaublich schlechte Übung und als solche ziemlich alltäglich (hey schau, es ist nicht abgestürzt!). Stellen Sie sicher, dass Sie den Code, der dies tut, aktualisieren, um ihn zumindest zu protokollieren. Entfernen Sie vorzugsweise die Behandlung falscher Ausnahmen vollständig. (Als Faustregel gilt: Wenn Sie die Ausnahme nicht kennen, sind Sie nicht bereit, damit umzugehen.) Wenn sie mit APIs im C-Stil interagiert, achten Sie auf gelöschte Fehlercode-Rückgabewerte, und stellen Sie sicher, dass dies der Fall ist Sie überprüfen die Fehlerstatusinformationen der Tools, mit denen Sie interagieren.

Angesichts der Tatsache, dass Ihr Testprogramm jetzt ordnungsgemäß mit Fehlern umgeht und Sie das so erstellte Protokoll gelesen haben, aber nichts den Fehler hervorhebt, sollten Sie nach Schnittstellen suchen, die Sie prüfen können. Gibt es eine Netzwerktransaktion, die unter dem Deckmantel stattfinden sollte? Wenn ja, schlagen Sie es mit Wireshark. Datenbanktransaktion? Versuchen Sie eine Abfrageprotokollierung oder überprüfen Sie den Status des Datenbankservers. Dateisystem oder Netzwerkfreigaben betroffen? Überprüfen Sie die Zwischendateien, oder verwenden Sie einen Debugger, um E / A zu verfolgen. Hardware I / O? Monitor und Sonde. Sei empirisch. Die Benutzerschnittstelle könnte bei Hintergrundoperationen, mit denen Sie nicht gerechnet haben, hängen bleiben.

Zuletzt: Keine Panik. Bleib cool und verfolge, was du ausprobiert hast. Wenn Sie es immer noch nicht finden können, muss es zu einem "bekannten Problem" werden, um an einem regnerischen Tag aufgespürt zu werden. Sie werden viel Material brauchen, um diese Entscheidung zu rechtfertigen, wenn es in diese Richtung gehen muss.


0

Reproduzierbare Bugs sind (relativ) einfach! Warum? Weil Sie den Code immer auf das Nötigste hacken können, bis der Fehler verschwindet, und dann zurückarbeiten, um herauszufinden, welcher Code ihn verursacht. Das ist also eine Methode. Es ist reproduzierbar, Sie haben das Lebewesen unter Ihrer Kontrolle. Sie können es stecken und damit experimentieren. Sie können es sogar zerlegen, wenn Sie möchten.

Ihr erstes Ziel ist es zu verstehen, warum der Fehler in Ihrem Code auftritt. Versuchen Sie zunächst nicht, das Problem zu beheben. Versuche es einfach zu verstehen . Wenn Sie versuchen, es zu beheben, ohne es zu verstehen, werden Sie herumhacken und wahrscheinlich technische Schulden einführen , selbst wenn Sie es lösen.

Schritt für Schritt durch das Verhalten der App. Beobachten Sie die Variablenwerte. Beobachten Sie den Kontrollfluss. Wo weicht das Verhalten zuerst von dem ab, was Sie nach Ihrem Verständnis erwarten? Verstehen Sie, wie das Betriebssystem Ereignisse an Ihre App sendet? Wenn Sie durch das "Black Box" -Problem behindert werden, können Sie die Quelle für kompilierte Bibliotheken / Frameworks beschaffen, so dass Sie bei Bedarf auf einer tieferen Ebene durchstarten können?

Haben Sie ein Commit in Ihrem Versionskontrollsystem, das diesen Fehler nicht verursacht? (Sie verwenden die Versionskontrolle, nicht wahr?) Wenn Sie ein solches Commit haben, können Sie eine binäre Suche im Verlauf durchführen, um genau herauszufinden, wo der Fehler aufgetreten ist.

Ihre Ziele sollten sein: (1) zu verstehen - die Ursache zu bestimmen und zu diesem Zweck zu versuchen, (2) das Verhalten der App im Detail zu untersuchen, zu verstehen ermöglicht Ihnen das zu tun

Aber auf keinen Fall wochenlang dort sitzen, wenn Sie wirklich festsitzen. Sie müssen es auch jemandem in Ihrer Organisation erzählen. Bitten Sie um Hilfe, wo immer Sie können und über einen bestimmten Punkt hinaus, ist es sicherlich Ihre Aufgabe, dem Management mitzuteilen, dass Sie das Gefühl haben, eine Barriere für den Fortschritt zu erreichen. Aber Sie werden wahrscheinlich in der Lage sein, dieses Problem zu lösen, wenn Sie es aus verschiedenen Blickwinkeln treffen, die alle auf Lernen und Verstehen ausgerichtet sind.

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.