In C und C ++ ist es sehr einfach, den folgenden Code mit einem schwerwiegenden Fehler zu schreiben.
char responseChar = getchar();
int confirmExit = 'y' == tolower(responseChar);
if (confirmExit = 1)
{
exit(0);
}
Der Fehler ist, dass die if-Anweisung hätte lauten sollen:
if (confirmExit == 1)
Wie codiert, wird es jedes Mal beendet, da die Zuweisung der confirmExit
Variablen erfolgt, und confirmExit
wird dann als Ergebnis des Ausdrucks verwendet.
Gibt es gute Möglichkeiten, solche Fehler zu vermeiden?
c++
coding-standards
DeveloperDon
quelle
quelle
if (confirmExit)
.a = b
odera == b
eine Bedingung zulässt .Antworten:
Die beste Technik besteht darin, die Warnstufe Ihres Compilers zu erhöhen. Es warnt Sie dann vor einer möglichen Zuordnung in der if-Bedingung.
Stellen Sie sicher, dass Sie Ihren Code mit Null-Warnungen kompilieren (was Sie trotzdem tun sollten). Wenn Sie pedantisch sein möchten, stellen Sie Ihren Compiler so ein, dass Warnungen als Fehler behandelt werden.
Die Verwendung von Yoda-Bedingungen (die Konstante auf die linke Seite setzen) war eine andere Technik, die vor etwa einem Jahrzehnt populär war. Sie erschweren jedoch das Lesen des Codes (und behalten ihn daher aufgrund der unnatürlichen Art des Lesens bei (es sei denn, Sie sind Yoda)) und bieten keinen größeren Nutzen als die Erhöhung der Warnstufe (was auch den zusätzlichen Nutzen von mehr Warnungen hat).
Warnungen sind wirklich logische Fehler im Code und sollten korrigiert werden.
quelle
if (0 == ret)
Grauen erwartet .a == b
!!0==a && 0==b || 1==a && 1==b || 2==a && 2==b || ...
(wiederholen Sie dies für alle möglichen Werte). Vergessen Sie nicht den obligatorischen...|| 22==a && 22==b || 23==a && 24==b || 25==a && 25==b ||
... Fehler, oder die Wartungsprogrammierer werden keinen Spaß haben.Sie könnten immer etwas radikales tun wie das Testen Ihrer Software. Ich meine nicht einmal automatisierte Komponententests, nur die Tests, die jeder erfahrene Entwickler aus Gewohnheit durch zweimaliges Ausführen seines neuen Codes durchführt, einmaliges Bestätigen des Ausgangs und einmaliges Nicht-Ausführen. Das ist der Grund, warum die meisten Programmierer es für kein Problem halten.
quelle
rc=MethodThatRarelyFails(); if(rc = SUCCESS){
mehr als einmal Menschen gesehen, die gebissen haben , besonders wenn die Methode nur unter Bedingungen versagt, die schwer zu testen sind.Ein traditioneller Weg, um die falsche Verwendung von Zuweisungen innerhalb eines Ausdrucks zu verhindern, besteht darin, die Konstante links und die Variable rechts anzuordnen.
Der Compiler meldet einen Fehler für die unzulässige Zuweisung zu einer Konstanten ähnlich der folgenden.
Die überarbeitete if-Bedingung wäre:
Wie die folgenden Kommentare zeigen, wird dies von vielen als unangemessene Methode angesehen.
quelle
Ich bin damit einverstanden, dass jeder "Compiler-Warnungen" sagt, aber ich möchte eine andere Technik hinzufügen: Code-Überprüfungen. Wenn Sie den gesamten Code überprüfen, der festgeschrieben wird, vorzugsweise bevor er festgeschrieben wird, ist es wahrscheinlich, dass diese Art von Dingen während der Überprüfung abgefangen wird.
quelle
Erstens schadet es nie, die Warnstufe zu erhöhen.
Wenn Sie nicht möchten, dass Ihre Bedingung das Ergebnis einer Zuweisung innerhalb der if-Anweisung selbst
if(1 == val)
testet, haben Sie im Laufe der Jahre mit vielen C- und C ++ - Programmierern zusammengearbeitet und noch nie gehört, dass es eine schlechte Sache ist, die Konstante zuerst zu vergleichen könnte dieses Konstrukt versuchen.Wenn Ihr Projektleiter dies billigt, machen Sie sich keine Sorgen darüber, was andere Leute denken. Der wahre Beweis ist, ob Sie oder jemand anderes Ihren Code in Monaten und Jahren verstehen können.
Wenn Sie jedoch beabsichtigen, das Ergebnis einer Zuweisung zu testen, hätte die Verwendung höherer Warnungen die Zuweisung zu einer Konstanten möglicherweise aufgefangen.
quelle
if ( auto myPtr = dynamic_cast<some_ptr>(testPtr) ) {
, dass es vermieden wird, dennullptr
Gültigkeitsbereich unbrauchbar zu machen, wenn die Besetzung fehlschlägt. Dies ist vermutlich der Grund, warum C ++ diese eingeschränkte Zuweisungsmöglichkeit innerhalb einer Bedingung hat. Im übrigen sollte eine Definition eine eigene Linie bekommen, würde ich sagen - viel einfacher auf einen Blick zu sehen und weniger anfällig für verschiedene Irrtümer.Spät zur Party wie immer, aber hier ist die statische Code-Analyse der Schlüssel
Die meisten IDEs bieten jetzt SCA über die syntaktische Prüfung des Compilers hinaus an. Es stehen auch andere Tools zur Verfügung, einschließlich derer, die die MISRA- (*) und / oder CERT-C-Richtlinien implementieren.
Erklärung: Ich bin Teil der MISRA C-Arbeitsgruppe, poste aber in persönlicher Eigenschaft. Ich bin auch unabhängig von Werkzeugherstellern
quelle
Verwenden Sie einfach die Zuweisung für die linke Hand. Compiler-Warnungen können hilfreich sein, aber Sie müssen sicherstellen, dass Sie die richtige Stufe erreichen. Andernfalls werden Sie entweder mit sinnlosen Warnungen überflutet oder erhalten keine Anweisungen, die Sie sehen möchten.
quelle