Ich möchte zwei Variablen vergleichen, um festzustellen, ob sie gleich sind, aber ich möchte, dass bei diesem Vergleich die Groß- und Kleinschreibung nicht berücksichtigt wird.
Dies würde beispielsweise zwischen Groß- und Kleinschreibung unterscheiden:
if($var1 == $var2){
...
}
Aber ich möchte, dass die Groß- und Kleinschreibung nicht berücksichtigt wird. Wie würde ich das angehen?
quelle
'A' = 'a'
ist wahr. Eine Referenz: dev.mysql.com/doc/refman/5.0/en/case-sensitivity.htmlmb_strtolower()
stattdessen.strcasecmp()
Gibt 0 zurück, wenn die Zeichenfolgen identisch sind (abgesehen von Fallvariationen), sodass Sie Folgendes verwenden können:if (strcasecmp($var1, $var2) == 0) { }
quelle
strcasecmp()
behandelt keine Multibyte-Zeichen, daher kann es nicht mit Unicode umgehen.Wenn sich Ihre Zeichenfolge in einer Einzelbyte-Codierung befindet, ist dies ganz einfach:
if(strtolower($var1) === strtolower($var2))
Wenn Ihre Zeichenfolge UTF-8 ist, müssen Sie die Komplexität von Unicode berücksichtigen: Kleinbuchstaben und Großbuchstaben sind keine bijektiven Funktionen. Wenn Sie also ein Kleinbuchstabenzeichen haben, transformieren Sie es in Großbuchstaben und transformieren Sie es Wenn Sie auf Kleinbuchstaben zurückgreifen, erhalten Sie möglicherweise nicht denselben Codepunkt (und dasselbe gilt, wenn Sie mit einem Großbuchstaben beginnen).
Z.B
Latin Capital Letter I with Dot Above, U+0130
) ist ein Großbuchstabe mit "i" (Latin Small Letter I, U+0069
) als Kleinbuchstabenvariante - und die Großbuchstabenvariante von "i" ist "I" (Latin Capital Letter I, U+0049
).Latin Small Letter Dotless I, U+0131
) ist ein Kleinbuchstaben mit "I" (Latin Capital Letter I, U+0049
) als Großbuchstabenvariante - und die Kleinbuchstabenvariante von "I" ist "i" (Latin Small Letter I, U+0069
)So
mb_strtolower('ı') === mb_strtolower('i')
gibt false zurück, auch wenn sie die gleichen Großbuchstaben haben. Wenn Sie wirklich eine Vergleichsfunktion für Zeichenfolgen ohne Berücksichtigung der Groß- und Kleinschreibung wünschen, müssen Sie diese mit der Groß- und Kleinschreibung vergleichen:if(mb_strtolower($string1) === mb_strtolower($string2) || mb_strtoupper($string1) === mb_strtoupper($string2))
Ich habe eine Abfrage für die Unicode-Datenbank von https://codepoints.net ( https://dumps.codepoints.net ) ausgeführt und 180 Codepunkte gefunden, für die ich ein anderes Zeichen gefunden habe, wenn ich Kleinbuchstaben verwendet habe Kleinbuchstaben und 8 Codepunkte, für die ich ein anderes Zeichen gefunden habe, als ich die Großbuchstaben eines Großbuchstabens genommen habe
Aber es wird schlimmer : Der gleiche Graphemcluster, den der Benutzer sieht, kann mehrere Arten der Codierung haben: "ä" kann als
Latin Small Letter a with Diaeresis (U+00E4)
oder alsLatin Small Letter A (U+0061)
und dargestellt werdenCombining Diaeresis (U+0308)
- und wenn Sie sie auf Byte-Ebene vergleichen, wird dies nicht true zurückgeben!Dafür gibt es in Unicode eine Lösung: Normalisierung ! Es gibt vier verschiedene Formen: NFC, NFD, NFKC, NFKD. Für den Zeichenfolgenvergleich sind NFC und NFD äquivalent und NFKC und NFKD sind äquivalent. Ich würde NFKC nehmen, da es kürzer als NFKD ist und "ff" (
Latin Small Ligature ff, U+FB00
) in zwei normale "f" umgewandelt wird (aber 2⁵ wird auch auf 25 erweitert ...).Die resultierende Funktion wird:
function mb_is_string_equal_ci($string1, $string2) { $string1_normalized = Normalizer::normalize($string1, Normalizer::FORM_KC); $string2_normalized = Normalizer::normalize($string2, Normalizer::FORM_KC); return mb_strtolower($string1_normalized) === mb_strtolower($string2_normalized) || mb_strtoupper($string1_normalized) === mb_strtoupper($string2_normalized); }
Bitte beachten Sie:
quelle
if(strtolower($var1) == strtolower($var2)){ }
quelle
Warum nicht:
if(strtolower($var1) == strtolower($var2)){ }
quelle
Verwenden Sie strcasecmp .
quelle