Brak {
lub z }
powodu nieprawidłowego wcięcia
Niedopasowane nawiasy klamrowe są wspólne dla gorzej sformatowanego kodu, takiego jak:
if((!($opt["uniQartz5.8"]!=$this->check58)) or (empty($_POST['poree']))) {if
($true) {echo"halp";} elseif((!$z)or%b){excSmthng(False,5.8)}elseif (False){
Jeśli Twój kod wygląda tak, zacznij od nowa! W przeciwnym razie będzie to niemożliwe do naprawienia dla ciebie lub kogokolwiek innego. Nie ma sensu pokazywać tego w Internecie, aby poprosić o pomoc.
Będziesz w stanie to naprawić tylko wtedy, gdy będziesz mógł wizualnie śledzić zagnieżdżoną strukturę i relację warunków warunkowych if / else i ich {
bloków kodu }
. Użyj swojego IDE, aby sprawdzić, czy wszystkie są sparowane.
if (true) {
if (false) {
…
}
elseif ($whatever) {
if ($something2) {
…
}
else {
…
}
}
else {
…
}
if (false) { // a second `if` tree
…
}
else {
…
}
}
elseif (false) {
…
}
Każde podwójne }
}
zamknie nie tylko gałąź, ale poprzednią strukturę warunków. Dlatego trzymaj się jednego stylu kodowania; nie mieszaj i nie dopasowuj zagnieżdżonych drzew if / else.
Oprócz spójności okazuje się, że pomocne jest również uniknięcie długich warunków. Użyj zmiennych tymczasowych lub funkcji, aby uniknąć nieczytelnych if
-wyrażeń.
IF
nie można używać w wyrażeniach
Zaskakująco częstym błędem nowicjusza jest próba użycia if
instrukcji w wyrażeniu, na przykład instrukcji print:
⇓
echo "<a href='" . if ($link == "example.org") { echo …
Co oczywiście jest nieważne.
Możesz użyć trójkowego warunkowego , ale uważaj na wpływ na czytelność.
echo "<a href='" . ($link ? "http://yes" : "http://no") . "</a>";
W przeciwnym razie przerwij takie konstrukcje wyjściowe: użyj wielu if
s i echo
s .
Jeszcze lepiej, użyj zmiennych tymczasowych i umieść swoje warunkowe przed:
if ($link) { $href = "yes"; } else { $href = "no"; }
echo "<a href='$href'>Link</a>";
Zdefiniowanie funkcji lub metod dla takich przypadków również często ma sens.
Bloki kontrolne nie zwracają „wyników”
Teraz jest to mniej powszechne, ale kilku programistów próbuje nawet traktować if
tak, jakby mogło zwrócić wynik :
$var = if ($x == $y) { "true" };
Który jest strukturalnie identyczny z użyciem if
w obrębie ciągu konkatenacji / wyrażenia.
- Ale struktury kontrolne (jeśli / foreach / while) nie mają „rezultatu” .
- Dosłowny ciąg „true” również byłby tylko nieważnym stwierdzeniem.
Musisz użyć przypisania w bloku kodu :
if ($x == $y) { $var = "true"; }
Alternatywnie skorzystaj z ?:
trójskładnikowego porównania.
If in If
Nie można zagnieżdżaćif
warunku:
⇓
if ($x == true and (if $y != false)) { ... }
Co jest oczywiście zbędne, ponieważ and
(lub or
) już umożliwia porównywanie łańcuchowe.
Zapomniane ;
średniki
Jeszcze raz: każdy blok kontrolny musi być instrukcją. Jeśli poprzedni fragment kodu nie jest zakończony średnikiem, to jest to gwarantowany błąd składniowy:
⇓
$var = 1 + 2 + 3
if (true) { … }
Przy okazji, ostatni wiersz w {…}
bloku kodu również potrzebuje średnika.
Średnik za wcześnie
Prawdopodobnie błędem jest obwinianie określonego stylu kodowania, ponieważ pułapkę tę zbyt łatwo przeoczyć:
⇓
if ($x == 5);
{
$y = 7;
}
else ←
{
$x = -1;
}
Co dzieje się częściej, niż można sobie wyobrazić.
- Po zakończeniu
if ()
wyrażenia za;
jego pomocą zostanie wykonana instrukcja void. ;
Staje się pusta {}
sama w sobie!
{…}
Ten sposób blok zostaje odłączony od if
, i zawsze uruchamiane.
- Więc
else
nie ma już związku z otwartą if
konstrukcją, dlatego doprowadziłoby to do nieoczekiwanego błędu składniowego T_ELSE.
Co również wyjaśnia podobnie subtelną odmianę tego błędu składniowego:
if ($x) { x_is_true(); }; else { something_else(); };
Gdzie ;
po bloku kodu {…}
kończy się cały if
konstrukt, else
składnia gałęzi składniowo.
Nie używa bloków kodu
Składniowo dozwolone jest pomijanie nawiasów klamrowych {
… }
dla bloków kodu w if
/ elseif
/ else
oddziałach. Który niestety jest stylem składni bardzo powszechnym dla niewersjonowanych koderów. (Przy fałszywym założeniu pisanie lub czytanie było szybsze).
Jest jednak bardzo prawdopodobne, że spowoduje to przekroczenie składni. Wcześniej czy później dodatkowe instrukcje znajdą się w gałęziach if / else:
if (true)
$x = 5;
elseif (false)
$x = 6;
$y = 7; ←
else
$z = 0;
Ale faktycznie korzysta bloki kodu, ty masz napisać {
... }
je jako takie!
Nawet doświadczeni programiści unikają składni bez ramienia lub przynajmniej rozumieją to jako wyjątek od reguły.
Else / Elseif w złej kolejności
Oczywiście jedną rzeczą do przypomnienia jest porządek warunkowy .
if ($a) { … }
else { … }
elseif ($b) { … }
↑
Możesz mieć tyle elseif
s, ile chcesz, ale musisz else
iść ostatni . Tak to jest.
Deklaracje klasowe
Jak wspomniano powyżej , nie można mieć instrukcji sterujących w deklaracji klasy:
class xyz {
if (true) {
function ($var) {}
}
W takich przypadkach albo zapomniałeś definicji funkcji , albo }
zbyt wcześnie ją zamknąłeś .
Nieoczekiwany T_ELSEIF / T_ELSE
Podczas mieszania PHP i HTML zamykanie }
dla if/elseif
musi być w tym samym bloku PHP, <?php ?>
co następny elseif/else
. To wygeneruje błąd jak zamknięcie }
na te if
potrzeby, aby być częścią elseif
:
<?php if ($x) { ?>
html
<?php } ?>
<?php elseif ($y) { ?>
html
<?php } ?>
Prawidłowa forma <?php } elseif
:
<?php if ($x) { ?>
html
<?php } elseif ($y) { ?>
html
<?php } ?>
Jest to mniej więcej odmiana nieprawidłowego wcięcia - przypuszczalnie często oparta na złych intencjach kodowania.
Nie można zacierać innych instrukcji między tokenami if
i elseif
/ / else
tokenami strukturalnymi:
if (true) {
}
echo "in between"; ←
elseif (false) {
}
?> text <?php ←
else {
}
Albo może wystąpić tylko w {…}
blokach kodu, a nie między tokenami struktury kontroli.
- To i tak nie miałoby sensu. To nie jest tak, że był jakiś „niezdefiniowany” stan, kiedy PHP przeskakuje między
if
i else
gałęziami.
- Musisz zdecydować, gdzie należy wydrukować wyciągi / lub czy trzeba je powtórzyć w obu gałęziach.
Nie możesz także rozdzielić if / else pomiędzy różne struktury kontrolne:
foreach ($array as $i) {
if ($i) { … }
}
else { … }
Nie ma związku składniowego między if
i else
. Zakres foreach
leksykalny kończy się na }
, więc if
kontynuacja struktury nie ma sensu .
T_ENDIF
Jeśli skarży się na nieoczekiwany T_ENDIF, używasz alternatywnego stylu składni if:
⋯ elseif:
⋯ else:
⋯ endif;
. O czym powinieneś pomyśleć dwa razy.
Częstą pułapką jest mylenie niesamowicie podobnego :
jelita grubego dla ;
średnika . (Objęte „Wczesnym średnikiem”)
Ponieważ wcięcie jest trudniejsze do śledzenia w plikach szablonów, tym bardziej, gdy używasz alternatywnej składni - jest prawdopodobne, endif;
że nie pasuje żaden if:
.
Użycie } endif;
jest podwójnym if
terminatorem.
Podczas gdy „nieoczekiwany koniec $” jest zwykle ceną za zapomniane zamknięcie }
klamry.
Przypisanie a porównanie
Nie jest to więc błąd składniowy, ale warto wspomnieć w tym kontekście:
⇓
if ($x = true) { }
else { do_false(); }
To nie jest porównanie ==
/ ===
, ale =
zadanie . Jest to dość subtelne i z łatwością poprowadzi niektórych użytkowników do bezradnej edycji całych bloków warunków. Najpierw uważaj na niezamierzone zadania - zawsze, gdy napotkasz błąd logiczny / złe zachowanie.