MongoDB enthält die $strLenBytes
und $strLenCP
Betreiber in seinem Aggregation-Pipeline-Framework. Diese Operatoren tun eine ähnliche, aber etwas andere Sache. In einigen Fällen liefern beide genau das gleiche Ergebnis, während in anderen Fällen die Ergebnisse unterschiedlich sind.
Hier ist ein kurzer Überblick über den Unterschied zwischen diesen beiden Operatoren.
Der Unterschied
Hier ist eine Definition der einzelnen Operatoren:
$strLenBytes
gibt die Anzahl der UTF-8-codierten Bytes zurück in der angegebenen Zeichenfolge$strLenCP
gibt die Anzahl der UTF-8-Codepunkte zurück in der angegebenen Zeichenfolge.
Beachten Sie den Unterschied in Fettschrift. Man gibt die Anzahl Bytes zurück , der andere gibt die Anzahl der Codepunkte zurück .
Bei der Arbeit mit englischen Strings entspricht die Anzahl der Bytes normalerweise der Anzahl der Codepunkte. Jeder Codepunkt verwendet ein Byte.
Wenn Sie jedoch mit anderen Sprachen arbeiten, die einen anderen Unicode-Block verwenden, stellen Sie möglicherweise fest, dass sich die Anzahl der Bytes auf zwei oder drei Bytes erhöht. Dies gilt auch, wenn Sie mit anderen Unicode-Codepunkten wie Symbolen, Emoji usw. arbeiten. In einigen Fällen kann ein einzelnes Zeichen 4 Bytes verwenden.
Beispiel
Angenommen, wir haben eine Sammlung namens unicode
mit folgenden Dokumenten:
{ "_id" :1, "data" :"é" }{ "_id" :2, "data" :"©" }{ "_id" :3, "data" :"℘" }Und jetzt wenden wir beide
$strLenBytes
an und$strLenCP
zum Datenfeld:db.unicode.aggregate( [ { $project: { _id: 0, data: 1, strLenCP: { $strLenCP: "$data" }, strLenBytes: { $strLenBytes: "$data" } } } ] )
Ergebnis:
{ "data" :"é", "strLenCP" :1, "strLenBytes" :2 }{ "data" :"©", "strLenCP" :1, "strLenBytes" :2 }{ "data" :„℘“, „strLenCP“ :1, „strLenBytes“ :3 }Wir können sehen, dass alle Zeichen nur einen Codepunkt verwenden, aber das erste Dokument verwendet zwei Bytes und die anderen beiden Dokumente verwenden jeweils drei Bytes.
Englische Zeichen
Angenommen, wir haben eine Sammlung namens
english
mit folgenden Dokumenten:{ "_id" :1, "data" :"Schneller Hund" }{ "_id" :2, "data" :"F" }{ "_id" :3, "data" :"a" }{ „_id“ :4, „data“ :„s“ }{ „_id“ :5, „data“ :„t“ }{ „_id“ :6, „data“ :„ “ }{ „_id“ :7, „Daten“ :„d“ }{ „_id“ :8, „Daten“ :„o“ }{ „_id“ :9, „Daten“ :„g“ }Und jetzt wenden wir beide
$strLenBytes
an und$strLenCP
zum Datenfeld:db.english.aggregate( [ { $project: { _id: 0, data: 1, strLenCP: { $strLenCP: "$data" }, strLenBytes: { $strLenBytes: "$data" } } } ] )
Ergebnis:
{ "data" :"Fast dog", "strLenCP" :8, "strLenBytes" :8 }{ "data" :"F", "strLenCP" :1, "strLenBytes" :1 }{ "data" :„a“, „strLenCP“ :1, „strLenBytes“ :1 }{ „data“ :„s“, „strLenCP“ :1, „strLenBytes“ :1 }{ „data“ :„t“, „strLenCP“ :1, "strLenBytes" :1 }{ "data" :" ", "strLenCP" :1, "strLenBytes" :1 }{ "data" :"d", "strLenCP" :1, "strLenBytes" :1 } { "data" :"o", "strLenCP" :1, "strLenBytes" :1 }{ "data" :"g", "strLenCP" :1, "strLenBytes" :1 }In diesem Fall verwenden alle Zeichen jeweils einen Codepunkt und ein Byte.
Thailändische Schriftzeichen
Hier ist ein Beispiel, das thailändische Zeichen verwendet, um zu demonstrieren, dass nicht alle Sprachen ein Byte pro Codepunkt verwenden.
Angenommen, wir haben eine Sammlung namens
thai
mit folgenden Dokumenten:{ "_id" :1, "data" :"ไม้เมือง" }{ "_id" :2, "data" :"ไ" }{ "_id" :3, "data" :"ม้" }{ „_id“ :4, „data“ :„เ“ }{ „_id“ :5, „data“ :„มื“ }{ „_id“ :6, „data“ :„อ“ }{ „_id“ :7 , "Daten":"§" }Folgendes passiert, wenn wir beide
$strLenBytes
anwenden und$strLenCP
zum Datenfeld:db.thai.aggregate( [ { $project: { _id: 0, data: 1, strLenCP: { $strLenCP: "$data" }, strLenBytes: { $strLenBytes: "$data" } } } ] )
Ergebnis:
{ "data" :"ไม้เมือง", "strLenCP" :8, "strLenBytes" :24 }{ "data" :"ไ", "strLenCP" :1, "strLenBytes" :3 }{ "data" :„ม้“, „strLenCP“ :2, „strLenBytes“ :6 }{ „data“ :„เ“, „strLenCP“ :1, „strLenBytes“ :3 }{ „data“ :„มื“, „strLenCP“ :2, „strLenBytes“ :6 }{ „data“ :„อ“, „strLenCP“ :1, „strLenBytes“ :3 }{ „data“ :„ง“, „strLenCP“ :1, „strLenBytes“ :3 }