2010-12-21 13 views
6

Das folgende Beispiel ist ein Auszug aus http://php.net/manual/de/control-structures.switch.phpProblem mit bedingtem Schalter

<?php 
$totaltime = 0; 
switch ($totaltime) { 

    case ($totaltime < 1): 
     echo "That was fast!"; 
     break; 

    case ($totaltime > 1): 
     echo "Not fast!"; 
     break; 

    case ($totaltime > 10): 
     echo "That's slooooow"; 
     break; 
} 

?> 

ich das Ergebnis wie erwartet „Das schnell war.“ Aber das tatsächliche Ergebnis ist "Nicht schnell!". Es wäre toll, wenn jemand mir erklären könnte warum?

Aber wenn ich einen weiteren Fall hinzufügen, case 0: echo "That was super fast!". Dann echo es richtig. "Das war super schnell!" Bitte helfen Sie mir, wie man eine bedingte Switch-Anweisung verwendet.

EDIT: -

Vielen Dank für Ihre Antworten. Ich bin in der Lage, das obige Problem zu überwinden, indem modifyong switch ($ totaltime), um (1)

+0

= nur Schalter einmal zu bewerten, Sie scheint falsch verwendet darauf – ajreal

Antwort

10

case ($totaltime < 1): bedeutet 1 zu PHP (die Gleichung liefert true)

case ($totaltime > 1): bedeutet 0 zu PHP (die Gleichung gibt false)

Seit $totaltime 0, Sie bekommen, dass die Ausgabe

Mit anderen Worten PHP vergleichen $totaltime auf das Ergebnis der Vergleiche.

EDIT über EDIT in OP:

Sie müssen der switch() -Aussage loszuwerden. Sie verwenden es nur, um problemlos mit verschiedenen Werten zu vergleichen und keine zusätzlichen Ausdrücke zu verwenden.

Ich meine, was mit

<?php 
$totaltime = 0; 

if ($totaltime < 1) { 
    echo "That was fast!"; 
} else if ($totaltime > 10) { 
    echo "That's slooooow"; 
} else if ($totaltime > 1) { 
    echo "Not fast!"; 
} 

?> 

EDIT falsch ist: Bitte beachten Sie, dass ich die letzten zwei geschaltet if-Anweisungen es wirklich funktioniert.

+0

- Es gibt überhaupt nichts falsch. Aber ich habe fast 20 Werte, für die ich vergleichen und Fehler anzeigen muss. Also dachte ich, dass Switch es readbale statt IF machen wird. – satya

+0

@lucky: aber Sie verstehen, dass es mit einer Menge von 'if() 'Aussagen viel besser lesbar ist? Es würde auch weniger Code bedeuten, was zu weniger Chancen für einen Fehler führen würde (das ist jedoch eher eine allgemeine Regel). – sjngm

1

Es scheint fast, dass dies ein boolescher Konvertierungsproblem ist.

Die erste case-Anweisung wird zu etwas anderem als 0 ausgewertet, so dass nicht getroffen wird.

Aber die zweite Case-Anweisung wird zu false ausgewertet, was 0 sein sollte, was gleichbedeutend ist mit dem, was Sie $ totaltime gesetzt haben.

1

Lucky

PHP-Schalter ist als Reihe von IF-Anweisungen gleichen. Die Fälle werden wie folgt ausgewertet:

Offensichtlich 0 == falsch für 2. IF ist wahr und daher das Ergebnis.

Danke, Vikas.

2

Sie verwenden keine Conditionals in den case Aussagen, nicht intuitiv sowieso. Das ist, was passiert:

case ($totaltime < 1): // Evaluates to 1. $totaltime is not 1, so no match. 
    case ($totaltime > 1): // Evaluates to 0. $totaltime is 0, so match. 

Im Grunde versucht man, ein else if Konstrukt als switch Konstrukt zu verwenden, aber die Funktionalität ist nicht da.Die Bedingungen werden nicht so ausgewertet, wie Sie es erwarten (wie in einem Block if). Sie suchen nur nach dem ersten Block case, der dem Wert entspricht, der im Block switch getestet wird.

0

Andere haben erwähnt, warum dies geschieht (Missbrauch einer Bedingung in der Fall-Anweisung), aber sie haben keine Alternativen angeboten. Der Schalter soll bestimmte Argumente wie {0, 1, 2, 3..100, 101} usw. abdecken. Er trennt bestimmte Argumente oder Bereiche, anstatt ein einfaches if/else (wie Sie es benutzt haben) auszuführen. Sie können Ihre Argumente neu schreiben, um es allerdings abziehen:

switch ($totaltime) { 

    case (0): 
     echo "That was fast!"; 
     break; 

    case (1..PHP_INT_MAX): 
     echo "Not fast!"; 
     break; 

    default: 
     echo "That's slooooow"; 
     break; 
} 

Hier sind die .. ermöglicht ein Bereich abgedeckt werden, so etwas von 1 bis integer max von diesem Fall bedeckt ist. Die 0 wird explizit behandelt und alle anderen (re: < 0) sind durch den Standardfall abgedeckt.

+0

+1, Danke für Ihre Antwort. Das ist was ich suche. wenn $ totaltime = 10; es ergibt sich "Das ist slooooow"; statt "Nicht schnell!"; – satya

+0

-1 PHP unterstützt keine Bereiche, die Sie in einem Schalter/Fall verwendet haben. Ihr 'case (1..PHP_INT_MAX):' gibt tatsächlich den verketteten Wert von 1 und PHP_INT_MAX (12147483647) zurück. Ich nehme an, Sie haben in letzter Zeit zu viel Pascal gemacht und mischen PHP und Pascal Syntax: p. – wimvds

+0

@wimvds: Danke für den Kommentar und die Info. Ich denke, ich habe in letzter Zeit zu viel Zeit in anderen Sprachen verbracht. –

2

Hate zu NECRO ein Beitrag, der bereits beantwortet wird, aber ich bin eher verwirrt, niemand hat die Schalter (wahr) Methode berührt.

Es gibt keine wirkliche Welt Geschwindigkeitsvorteil von beiden Verfahren

In einigen Fällen kann der Schalter war schneller, andere die, wenn schneller war, aber nur um Bruchteile eines Mikro (48,16 & mgr; s vs 49,11 & mgr; s schneller schalten als wenn).

EDIT

Und ich sehe jetzt die OP tat das gleiche ...

<?php 
for ($totaltime = 0; $totaltime < 11; $totaltime += 0.5) { 
    switch (true) { 
     case ($totaltime < 1): 
      echo $totaltime . " That was fast!\n"; 
      break; 
     case ($totaltime < 10): 
      echo $totaltime . " Not fast!\n"; 
      break; 
     default: 
      echo $totaltime . " That's slooooow\n"; 
      break; 
    } 
} 

Ergebnisse: https://3v4l.org/d71lZ

0 That was fast! 
0.5 That was fast! 
1 Not fast! 
1.5 Not fast! 
2 Not fast! 
2.5 Not fast! 
3 Not fast! 
3.5 Not fast! 
4 Not fast! 
4.5 Not fast! 
5 Not fast! 
5.5 Not fast! 
6 Not fast! 
6.5 Not fast! 
7 Not fast! 
7.5 Not fast! 
8 Not fast! 
8.5 Not fast! 
9 Not fast! 
9.5 Not fast! 
10 That's slooooow 
10.5 That's slooooow