2012-12-28 3 views
7

zu erreichen Jedes Mal, wenn ich einen bestimmten Weg von Code ausüben will, die sonst nur unter einem schwer zu erreichen wären zu reproduzieren condition wie:Testen ein schwieriger Codepfad

if (condition) { code to be tested } 

ich es mit einem true Wert or:

if (true || condition) { code to be tested } 

Gibt es einen eleganteren Ansatz?

+0

Möchten Sie den Code über den Debugger ausführen? Ich würde empfehlen, dies in "Unit Testing" zu untersuchen. Eine spöttische Lösung kann dazu beitragen, dass Ihr Code testbar wird.Wenn Sie es als Komponententest schreiben, können Sie jetzt nicht nur Ihren Code testen, sondern auch den Test behalten! –

Antwort

13

Ich denke, mehr elegant way verwendet the logical negation operator (!) wie;

if (!condition) { code to be tested } 

aber sicherer Weg zum Debuggen oder Testzwecke SiePräprozessordirektive verwenden können (wie pro mein commet). Wenn Sie den Test abgeschlossen haben einfach entfernen oder #define UnreachableTest

#define UnreachableTest //should be on the top of the class/page 

#if (UnreachableTest) 
    condition = !condition; //or 
    condition = true; 
#endif 

if (condition) { code to be tested } 
+0

nicht betrifft Ja, es sieht mir mehr aus elegant. Mit dem einzigen Haken, dass es nicht funktionieren würde, wenn die Bedingung erfüllt ist. Aber ich mag es und ich denke, es wäre in den meisten Anwendungsfällen gut. –

+5

In diesem Fall können Sie eine 'Präprozessordirektive' verwenden, um die Bedingung für Testzwecke während des Debuggens zu ändern. Wie; '#define UnreachableTest' an der Spitze ...' #if (UnreachableTest) condition =! condition # endif' Dann ist Ihr aktueller Code zu folgen. – Kaf

+5

Entschuldigung, ich muss eine -1 auf diese Antwort geben. Dies ist ein sehr schlechter Code-Geruch, um die logische Bedingung zum Testen zu ändern. Es ist gefährlich, da es dazu führen könnte, dass jemand vergisst, das "!" und am Ende mit Produktionscode, der die Bedingung umgedreht hat und Fehler/Bugs erzeugt. –

13

Eine elegantere Lösung sind Mocks. Treffen Sie Entscheidungen basierend auf Abhängigkeiten oder Parameter:

var mock = new Mock<IFoo>(); 
mock.Setup(foo => foo.IsBar).Returns(true); 
var sut = new Sut(mock.Object); 
sut.DoSomething(); 

Und in Ihrem System im Test:

public void DoSomething() 
{ 
    if (_foo.IsBar) 
     // code path to test 
} 
+1

lesen Sie die Frage vor dem Posten - 'wollen einen bestimmten Pfad des Codes ausüben, der sonst nur unter schwierig zu reproduzierenden Bedingungen erreicht würde 'OP Ziel ist es, den Code innerhalb' if' zu testen, dh dort mit 100% Chance gehen – Nogard

+4

@Nogard Ich erwähnte die Verwendung von Mocks. Und fügte Codebeispiel hinzu. Lesen Sie die Antwort bis zum Ende, bevor Sie kommentieren. –

+1

Sicher sah ich das, aber Ihre vorbearbeitete Antwort (die ich kommentierte) sagte nur "schwierig zu reproduzieren Zustand" - spöttisch als auch könnte es verwenden. Dann wurde Mock-Probe hinzugefügt und es löst OP-Problem. – Nogard

2

Ich nehme an, ändern dieses Szenario kein Unit-Test ist, da sie nicht in der Frage erwähnt wurde. Der einfachste Weg, um Code wie diesen on-the-fly zu testen, ist die Verwendung des Befehls Set Next Statement des Debuggers.

Legen Sie ggf. einen Haltepunkt für die if() -Anweisung fest, oder führen Sie den Code schrittweise aus, bis er diese Anweisung erreicht. Klicken Sie dann mit der rechten Maustaste auf die nächste Zeile im if() - Anweisungshauptteil und wählen Sie "Nächste Anweisung festlegen". Der Code wird wieder an dieser Zeile ausgeführt, wobei if() komplett übersprungen wird.

+0

Gut +1. Ich werde es sicher benutzen. Aber in diesem speziellen Fall, in dem ich diesen Weg mindestens ein paar Mal zurücklegen möchte, ist es peinlich. –

3

Ihr Ansatz, mit "wahr oder", und der Ansatz von if (! Bedingung) sind die einfachsten. Hier ist ein Ansatz, den ich für große Programme mag

Erstellen Sie eine Funktion, nennen wir es Testme (const String). Anstatt true in if test einzufügen, fügen Sie testme mit einer Zeichenfolge ein, die diesen Codeabschnitt identifiziert.

if (testme("Location 123") || condition) { code to be tested } 

Dann eine Art von Konfigurationsdatei verwenden oder Argumente für Ihr Programm (i bevorzugen config), können Sie total steuern, wenn testme ("Location 123") true zurück. UND Sie können die gleiche Funktion an vielen Orten verwenden. Ändern Sie einfach die Konfigurationsdatei, um jeden zu testen.

+0

+1. Ich habe eine boolesche Variable verwendet, die an anderer Stelle für diesen Zweck definiert wurde. –

2

Geben Sie den zu testenden Code in eine separate Methode ein. Dann können Sie die Methode aufrufen und die Bedingung umgehen. Jetzt müssen Sie sich nicht mehr darum kümmern, "wahr" hinzuzufügen oder, was noch wichtiger ist, zu vergessen, es zu entfernen.

Sie können auch Komponententests für die Methode hinzufügen, damit Sie die übergebenen Parameter ändern und alle gewünschten Szenarien testen können.

Verwandte Themen