Zjištění příslušnosti do seznamu

Školení, která pořádám

Pokud chceme zjistit, jestli proměnná odpovídá nějakému prvku v seznamu, můžeme to udělat několika způsoby:

<?php
($a == "a" || $a == "b" || $a == "c" || $a == "d");
in_array($a, array("a", "b", "c", "d"));
preg_match('~^(a|b|c|d)$~', $a);
?>

První způsob je dlouhý na zápis a neumožňuje prvky seznamu definovat mimo samotnou podmínku např. v proměnné. Používám ho tedy pouze v případě, že seznam má pouze dva, maximálně tři prvky a $a není volání funkce. Druhý způsob bych označil za tradiční řešení a třetí způsob je sice poněkud hůře čitelný, ale má tu výhodu, že prvky seznamu mohou být nejen konstantní řetězce, ale i regulární výrazy. Pokud je seznam definován mimo podmínku a je dlouhý, stojí za zvážení uložit prvky jako klíče pole a následně testovat isset($prvky[$a]), což by mělo být teoreticky rychlejší, protože vypočtení hashe a přímý přístup k prvku je rychlejší než procházení celého pole funkcí in_array. Především v Céčkových zdrojácích je možné vidět také následující způsob, kvůli jeho neúspornosti ale nejsem jeho zastáncem.

<?php
switch ($a) {
    case 'a':
    case 'b':
    case 'c':
    case 'd':
        ;
}
?>
Jakub Vrána, Dobře míněné rady, 14.9.2005, diskuse: 7 (nové: 0)

Diskuse

Lukas:

Ja celkem casto pouzivam switch a nevidim v tom nic horsiho nez zapis in_array nebo preg_match.

Z jakeho duvodu nejsi jeho zastancem (switch)?

Llaik:

Mozna proto, ze zabira dost mista.. na druhou stranu  bych tipl, ze switch ze vsech reseni bude mozna nejrychlejsi, ne? (coz je ve vetsine pripadu phpka docela putna,ale.. :))

ikona Jakub Vrána OpenID:

Přesně tak, je s tím hodně psaní a nezdá se mi to ve většině případů přehledné. O rychlostní rozdíly v řádu procent až tak nejde (http://php.vrana.cz/optimalizace-kodu.php), prvořadá je pro mě čitelnost a rozšiřitelnost.

TimeLord:

"switch" je podla mna citatelny viac nez dost a je rychlejsi.

Zalezi samozrejme od sposobu pouzitia, niekde sa viac hodi "switch", inde "if".

Na druhej strane, robit jednoznacne prehlasenie, ze "switch a nic ine" by bolo zase unahlene.

johno:

Ak je ten zoznam fakt dlhé, tak to robím takto:
<?php
    $list
= array(
        "a" => 1,
        "b" => 1,
        "c" => 1,
        // ...
    );
   
    $isThere
= array_key_exists($a, $list);
?>

Je to potom oveľa rýchlejšie, pretože nemusím ísť lineárne O(n) cez pole, ale cez hash a teda konštantne O(1). Opakujem, toto zrýchlenie sa poriadne prejaví až pri veľkých poliach. Rádovo tak od stovky alebo tisícovky položiek.

Používejte diakritiku. Vstup se chápe jako čistý text, ale URL budou převedeny na odkazy a PHP kód uzavřený do <?php ?> bude zvýrazněn. Pokud máte dotaz, který nesouvisí s článkem, zkuste raději diskusi o PHP, zde se odpovědi pravděpodobně nedočkáte.

Jméno: URL: Reakce na: johno

ikona Jakub Vrána OpenID:

Ano, je to zmíněné i v článku, pouze místo array_key_exists($a, $list) je použito isst($list[$a]).

johno:

Aha, pardón.
avatar © 2005-2021 Jakub Vrána. Publikované texty můžete přetiskovat pouze se svolením autora. Ukázky kódu smíte používat s uvedením autora a URL tohoto webu bez dalších omezení Creative Commons. Můžeme si tykat. Skripty předpokládají nastavení: magic_quotes_gpc=Off, magic_quotes_runtime=Off, error_reporting=E_ALL & ~E_NOTICE a očekávají předchozí zavolání mysql_set_charset. Skripty by měly být funkční v PHP >= 4.3 a PHP >= 5.0.