MongoDB
 sql >> Datenbank >  >> NoSQL >> MongoDB

MongoDB $substrBytes

In MongoDB sind die $substrBytes Der Aggregations-Pipeline-Operator gibt die Teilzeichenfolge einer Zeichenfolge basierend auf den angegebenen UTF-8-codierten Byte-Indizes zurück.

Syntax

Die Syntax lautet wie folgt:

{ $substrBytes: [ <string expression>, <byte index>, <byte count> ] }

Wo:

  • <string expression> ist die Saite. Es kann jeder gültige Ausdruck sein, solange er in einen String aufgelöst wird.
  • <byte index> ist, wo der Teilstring beginnen soll. Es kann jeder gültige Ausdruck sein, solange er in eine nicht negative Ganzzahl oder Zahl aufgelöst wird, die als Ganzzahl dargestellt werden kann.
  • <byte count> ist, wie viele Bytes die Teilzeichenfolge fortgesetzt werden soll. Es kann jeder gültige Ausdruck sein, solange er in eine nicht negative Ganzzahl oder Zahl aufgelöst wird, die als Ganzzahl dargestellt werden kann.

Beispiel

Stellen Sie sich vor, wir haben eine Sammlung namens tests mit folgendem Dokument:

{ "_id" : 1, "data" : "Red Firetruck" }

Wir können $substrBytes verwenden so:

db.test.aggregate(
   [
     { $match: { _id: { $in: [ 1 ] } } },
     {
       $project:
          {
            _id: 0,
            data: 1,
            result: { $substrBytes: [ "$data", 0, 3 ] }
          }
     }
   ]
)

Ergebnis:

{ "data" : "Red Firetruck", "result" : "Red" }

Der Index beginnt bei Null, und so begann unser Teilstring am Anfang des Strings und dauerte drei Bytes.

In diesem Fall verwenden wir englische Zeichen und jedes Zeichen ist ein Byte. Dies macht es uns leicht zu zählen, wie viele Bytes verwendet werden sollen.

Lassen Sie uns ein weiteres Beispiel ausführen:

db.test.aggregate(
   [
     { $match: { _id: { $in: [ 1 ] } } },
     {
       $project:
          {
            _id: 0,
            data: 1,
            result_1: { $substrBytes: [ "$data", 4, 4 ] },
            result_2: { $substrBytes: [ "$data", 8, 5 ] },
            result_3: { $substrBytes: [ "$data", 8, 20 ] }
          }
     }
   ]
).pretty()

Ergebnis:

{
	"data" : "Red Firetruck",
	"result_1" : "Fire",
	"result_2" : "truck",
	"result_3" : "truck"
}

Beachten Sie, dass wir in unserem dritten Ergebnis mehr Bytes angegeben haben, als verfügbar waren, aber es wurden einfach alle Zeichen bis zum Ende der Zeichenfolge zurückgegeben.

Multibyte-Zeichen

Einige Zeichen verwenden mehr als ein Byte. Manche verwenden zwei, manche drei und manche sogar vier.

Hier ist ein Beispiel für ein Dokument, das eine Reihe von Symbolen enthält:

{ "_id" : 2, "data" : "©♡★✪☆" }

Jedes dieser Zeichen verwendet mehr als ein Byte. Das bedeutet, dass wir beim Extrahieren eines Teilstrings vorsichtig sein müssen. Wir müssen sicher sein, dass unser Ausgangspunkt nicht in der Mitte eines Charakters beginnt. Wenn dies der Fall ist, tritt ein Fehler auf. Ebenso müssen wir sicherstellen, dass unser Endpunkt nicht auf halbem Weg durch einen Charakter endet.

Lassen Sie uns zunächst $substrBytes anwenden ohne einen Fehler zu bewirken:

db.test.aggregate(
   [
     { $match: { _id: { $in: [ 2 ] } } },
     {
       $project:
          {
            _id: 0,
            data: 1,
            bytes: { $strLenBytes: [ "$data" ] },
            result: { $substrBytes: [ "$data", 0, 5 ] }
          }
     }
   ]
)

Ergebnis:

{ "data" : "©♡★✪☆", "bytes" : 14, "result" : "©♡" }

Basierend auf unserem Ausgangspunkt von 0 und unsere Bytelänge von 5 , erhalten wir zwei Zeichen in unserer Ergebnismenge. Daher können wir sehen, dass die ersten beiden Zeichen 5 Bytes verwenden.

In diesem Beispiel habe ich auch $strLenBytes verwendet um die Gesamtzahl der Bytes in der Zeichenfolge zurückzugeben. Ich habe dies hauptsächlich getan, um zu zeigen, dass die fünf Zeichen 14 Bytes (mehrere Bytes pro Zeichen) verwenden.

Hier ist ein leicht modifiziertes Beispiel, das jedes der beiden zurückgegebenen Zeichen zurückgibt:

db.test.aggregate(
   [
     { $match: { _id: { $in: [ 2 ] } } },
     {
       $project:
          {
            _id: 0,
            data: 1,
            r1: { $substrBytes: [ "$data", 0, 2 ] },
            r2: { $substrBytes: [ "$data", 2, 3 ] }
          }
     }
   ]
)

Ergebnis:

{ "data" : "©♡★✪☆", "r1" : "©", "r2" : "♡" }

Wir können sehen, dass das erste Zeichen zwei Bytes und das zweite Zeichen drei verwendet.

Falscher Ausgangspunkt

Wenn Ihr Startpunkt bei der Hälfte eines Zeichens liegt, tritt ein Fehler auf.

Beispiel:

db.test.aggregate(
   [
     { $match: { _id: { $in: [ 2 ] } } },
     {
       $project:
          {
            _id: 0,
            data: 1,
            result: { $substrBytes: [ "$data", 1, 2 ] }
          }
     }
   ]
)

Ergebnis:

Error: command failed: {
	"ok" : 0,
	"errmsg" : "$substrBytes:  Invalid range, starting index is a UTF-8 continuation byte.",
	"code" : 28656,
	"codeName" : "Location28656"
} : aggregate failed :
[email protected]/mongo/shell/utils.js:25:13
[email protected]/mongo/shell/assert.js:18:14
[email protected]/mongo/shell/assert.js:639:17
[email protected]/mongo/shell/assert.js:729:16
[email protected]/mongo/shell/db.js:266:5
[email protected]/mongo/shell/collection.js:1058:12
@(shell):1:1

Dieser Fehler teilt uns mit, dass der starting index is a UTF-8 continuation byte ist . Mit anderen Worten, wir haben versucht, mitten in einem Charakter zu beginnen.

Falscher Endpunkt

Genauso ist es mit dem Endpunkt. Wenn Ihr Endpunkt auf halbem Weg durch ein Zeichen ist, tritt ein Fehler auf.

Beispiel:

db.test.aggregate(
   [
     { $match: { _id: { $in: [ 2 ] } } },
     {
       $project:
          {
            _id: 0,
            data: 1,
            result: { $substrBytes: [ "$data", 0, 1 ] }
          }
     }
   ]
)

Ergebnis:

Error: command failed: {
	"ok" : 0,
	"errmsg" : "$substrBytes:  Invalid range, ending index is in the middle of a UTF-8 character.",
	"code" : 28657,
	"codeName" : "Location28657"
} : aggregate failed :
[email protected]/mongo/shell/utils.js:25:13
[email protected]/mongo/shell/assert.js:18:14
[email protected]/mongo/shell/assert.js:639:17
[email protected]/mongo/shell/assert.js:729:16
[email protected]/mongo/shell/db.js:266:5
[email protected]/mongo/shell/collection.js:1058:12
@(shell):1:1

Dieses Mal teilt es uns mit, dass der ending index is in the middle of a UTF-8 character steht .