Erste Schritte mit MongoDB - Teil 2

Sind Sie bereit, weiter über MongoDB zu lernen, eine der coolsten Technologien für Webentwickler? In diesem zweiten Teil der Serie gehen wir von den Grundlagen über erweiterte Abfragen - mit bedingten Operatoren - und MapReduce über.


Über die Grundlagen hinausgehen

Zuvor haben wir die Grundlagen und den Einstieg in mongoDB beschrieben, eine der absolut besten NoSQL-Implementierungen. Wir haben untersucht, wie man es installiert, eine Basisdatenbank erstellt und dann die grundlegenden Vorgänge daran ausführt:

  • Suche
  • aktualisieren
  • löschen

Darüber hinaus haben wir über die Verwendung von Selektoren nachgedacht, wie Sie mit MongoDB auf eine effektivere Art und Weise interagieren können. Selektoren geben uns die Möglichkeit, eine viel feinere Kontrolle zu haben und die Daten, die wir wirklich wollen, zu finden.

Nun, das ist alles gut und gut, um damit anzufangen, aber wenn Sie eine echte Anwendung schreiben möchten, müssen Sie noch viel weiter gehen. Nun, das ist immer noch ein fertig machen Serie, aber ich möchte Sie für die Möglichkeiten des dokumentenorientierten Arbeitens begeistern. Ich möchte Sie dazu begeistern, diese großartige Technologie zu Ihrer eigenen zu machen und sie so mächtig wie möglich zu nutzen, um fantastische Anwendungen zu erstellen.

Heute werden wir die Abfragen vom letzten Mal erweitern und zwei wichtige Aspekte von mongoDB lernen:

  • Erweiterte Abfragen
  • Karte verkleinern

Erweiterte Abfragen

Zuvor haben wir uns grundlegende Fragen angeschaut und Selektoren vorgestellt. Jetzt werden wir uns mit fortgeschritteneren Abfragen befassen, indem wir auf zwei Arten auf der vorherigen Arbeit aufbauen:

  • Bedingte Operatoren
  • Reguläre Ausdrücke

Jede dieser Optionen gibt uns nach und nach eine genauere Kontrolle über die Abfragen, die wir schreiben können, und folglich die Informationen, die wir aus unseren MongoDB-Datenbanken extrahieren können.

Bedingte Operatoren

Bedingungsoperatoren sind, wie der Name schon sagt, Operatoren für die Abfrage von Abfragen, die die Bedingungen präzisieren, die die Abfrage erfüllen muss, wenn Daten aus der Datenbank extrahiert werden. Es gibt eine Reihe von ihnen, aber heute werde ich mich auf 9 Schlüssel konzentrieren. Diese sind:

  • $ lt - Der Wert muss unter dem Bedingungswert liegen
  • $ gt - Der Wert muss größer als der Bedingte sein
  • $ lte - Wert muss kleiner oder gleich der Bedingung sein
  • $ gte - value muss größer oder gleich der Bedingung sein
  • $ in - Der Wert muss sich in einer Reihe von Bedingungen befinden
  • $ neun - Der Wert darf NICHT in einer Reihe von Bedingungen enthalten sein
  • $ nicht - Der Wert muss einer Bedingung entsprechen

Schauen wir uns die Reihe nach an. Öffnen Sie Ihr Terminal und machen Sie sich bereit, die ursprüngliche Datenbank aus dem ersten Teil dieser Serie zu verwenden (Vormodifikationen). Um dieses Tutorial zu vereinfachen, nehmen wir eine geringfügige Änderung an der Datenbank vor. Wir geben jedem Dokument in unserer Sammlung ein Altersattribut. Führen Sie dazu die folgende Änderungsabfrage aus:

 db.nettuts.update ("_ id": ObjectId ("4ef224be0fec2806da6e9b27"), "$ set": "age": 18); db.nettuts.update ("_ id": ObjectId ("4ef224bf0fec2806da6e9b28"), "$ set": "age": 45); db.nettuts.update ("_ id": ObjectId ("4ef224bf0fec2806da6e9b29"), "$ set": "age": 65); db.nettuts.update ("_ id": ObjectId ("4ef224bf0fec2806da6e9b2a"), "$ set": "age": 43); db.nettuts.update ("_ id": ObjectId ("4ef224bf0fec2806da6e9b2b"), "$ set": "age": 22); db.nettuts.update ("_ id": ObjectId ("4ef224bf0fec2806da6e9b2c"), "$ set": "age": 45); db.nettuts.update ("_ id": ObjectId ("4ef224bf0fec2806da6e9b2d"), "$ set": "age": 33);

Wenn alles in Ordnung ist, können Sie ein "Alle suchen" ausführen, und Sie erhalten die folgende Ausgabe:

 db.nettuts.find (); "_id": ObjectId ("4ef224be0fec2806da6e9b27"), "age": 18, "dob": "21/04/1978", "first": "matthew", "gender": "m", "hair_colour": "braun", "letzte": "Setter", "Nationalität": "Australier", "Beruf": "Entwickler" "_id": ObjectId ("4ef224bf0fec2806da6e9b28"), "Alter": 45, "dob": "26/03/1940", "first": "james", "gender": "m", "hair_colour": "braun", "last": "caan", "nationality": "american", "beruf" ":" actor " " _id ": ObjectId (" 4ef224bf0fec2806da6e9b29 ")," age ": 65," dob ":" 03/06/1925 "," first ":" arnold "," gender ":" m "," haarfarbe ":" braun "," letzte ":" schwarzenegger "," nationalität ":" amerikanisch "," beruf ":" schauspieler " " _id ": ObjectId (" 4ef224bf0fec2806da6e9b2a ")," alter ": 43, "dob": "21/04/1978", "first": "tony", "gender": "m", "hair_colour": "brown", "last": "curtis", "nationality": "amerikanisch", "beruf": "entwickler" "_id": ObjectId ("4ef224bf0fec2806da6e9b2b"), "age": 22, "dob": "22/11/1958", "first": "jamie lee" , "gender": "f", "hair" _colour ":" brown "," last ":" curtis "," nationality ":" american "," besetzung ":" actor " " _id ": ObjectId (" 4ef224bf0fec2806da6e9b2c ")," age ": 45," dob ":" 14/03/1933 "," first ":" michael "," gender ":" m "," hair_colour ":" brown "," last ":" caine "," nationality ":" english " , "Beruf": "Schauspieler" "_id": ObjectId ("4ef224bf0fec2806da6e9b2d"), "age": 33, "dob": "09/12/1934", "first": "judi", "gender" : "f", "hair_colour": "white", "last": "dench", "nationality": "english", "Occupation": "Schauspielerin"

$ lt / $ lte

Jetzt suchen wir alle Akteure, die weniger als 40 sind. Führen Sie dazu die folgende Abfrage aus:

 db.nettuts.find ("age": "$ lt": 40);

Nach dem Ausführen dieser Abfrage wird die folgende Ausgabe angezeigt:

 "_id": ObjectId ("4ef224be0fec2806da6e9b27"), "age": 18, "dob": "21/04/1978", "first": "matthew", "gender": "m", "hair_colour": "Braun", "Letzter": "Setter", "Nationalität": "Australier", "Beruf": "Entwickler" "_id": ObjectId ("4ef224bf0fec2806da6e9b2b"), "Alter": 22, "dob": "22/11/1958", "first": "jamie lee", "gender": "f", "hair_colour": "brown", "last": "curtis", "nationality": "american", " Beruf ":" Schauspieler " " _id ": ObjectId (" 4ef224bf0fec2806da6e9b2d ")," age ": 33," dob ":" 09/12/1934 "," erster ":" judi "," gender ":" f "," haarfarbe ":" weiß "," letzte ":" dench "," nationalität ":" englisch "," beruf ":" schauspielerin "

Was ist mit denen, die weniger als 40 Jahre alt sind? Führen Sie die folgende Abfrage aus, um dieses Ergebnis zurückzugeben:

 db.nettuts.find ("age": "$ lte": 40);

Dies gibt die folgende Liste zurück:

 "_id": ObjectId ("4ef224be0fec2806da6e9b27"), "age": 18, "dob": "21/04/1978", "first": "matthew", "gender": "m", "hair_colour": "Braun", "Letzter": "Setter", "Nationalität": "Australier", "Beruf": "Entwickler" "_id": ObjectId ("4ef224bf0fec2806da6e9b2b"), "Alter": 22, "dob": "22/11/1958", "first": "jamie lee", "gender": "f", "hair_colour": "brown", "last": "curtis", "nationality": "american", " Beruf ":" Schauspieler " " _id ": ObjectId (" 4ef224bf0fec2806da6e9b2d ")," age ": 33," dob ":" 09/12/1934 "," erster ":" judi "," gender ":" f "," haarfarbe ":" weiß "," letzte ":" dench "," nationalität ":" englisch "," beruf ":" schauspielerin "

$ gt / $ gte

Lassen Sie uns nun alle Schauspieler finden, die älter als 47 sind. Führen Sie die folgende Abfrage aus, um diese Liste zu finden:

 db.nettuts.find ('age': '$ gt': 47);

Sie erhalten dann folgende Ausgabe:

 "_id": ObjectId ("4ef224bf0fec2806da6e9b29"), "age": 65, "dob": "03/06/1925", "first": "arnold", "gender": "m", "hair_colour": "braun", "zuletzt": "schwarzenegger", "nationalität": "amerikanisch", "beruf": "schauspieler"

Was ist inklusive von 40?

 db.nettuts.find ('age': '$ gte': 47);

Da es nur eine Person über 47 gibt, werden die zurückgegebenen Daten nicht geändert.

$ in / $ neun

Wie finden Sie Informationen anhand einer Kriterienliste? Diese ersten waren in Ordnung, aber durchaus trivial. Schauen wir uns nun an, welche der Personen, die wir haben, entweder Schauspieler oder Entwickler sind. Mit der folgenden Abfrage werden wir das herausfinden (um die Lesbarkeit zu verbessern, haben wir die Schlüssel beschränkt, die auf den Vor- und Nachnamen zurückgegeben werden):

 db.nettuts.find ('Occupation': '$ in': ["actor", "developer"], "first": 1, "last": 1);

Diese Abfrage liefert die folgende Ausgabe:

 "_id": ObjectId ("4ef224be0fec2806da6e9b27"), "first": "matthew", "last": "setter" "_id": ObjectId ("4ef224bf0fec2806da6e9b28"), "first": "james", "last" ":" caan " " _id ": ObjectId (" 4ef224bf0fec2806da6e9b29 ")," first ":" arnold "," last ":" schwarzenegger "" "_id": ObjectId ("4ef224bf0fec2806da6e9b2a"), "first": "tony", "last": "curtis" "_id": ObjectId ("4ef224bf0fec2806da6e9b2b"), "first": "jamie lee", "last": "curtis" "_id": ObjectId ("4ef224bf0fec2806da6b9b2b2cb2bbc ")," first ":" michael "," last ":" caine "

Sie können sehen, dass wir das Gegenteil davon bekommen können, indem Sie verwenden $ neungenauso einfach.

Lassen Sie uns dies etwas mehr Spaß machen und einige der Operatoren kombinieren. Nehmen wir an, wir wollen nach allen Menschen suchen, die entweder männlich oder entwicklungsfähig sind und weniger als 40 Jahre alt sind.

Das ist jetzt ein kleiner Schluck, aber mit den Operatoren, die wir bisher verwendet haben - durchaus erreichbar. Lassen Sie uns durcharbeiten und Sie werden sehen. Schauen Sie sich die folgende Abfrage an:

 db.nettuts.find ($ oder: ["gender": "m", "Occupation": "developer"]], "age": "$ gt": 40, "first": 1 , "letzte": 1, "Beruf": 1, "dob": 1);

Sie können sehen, dass wir festgelegt haben, dass entweder das Geschlecht männlich sein kann oder der Beruf ein Entwickler in der $ oder Bedingung und dann ein hinzugefügt und Bedingung des Alters ist größer als 4.

Dafür erhalten wir folgende Ergebnisse:

 "_id": ObjectId ("4ef22e522893ba6797bf8cb6"), "first": "matthew", "last": "setter", "dob": "21/04/1978", "occupation": "developer" " _id ": ObjectId (" 4ef22e522893ba6797bf8cb9 ")," first ":" tony "," last ":" curtis "," dob ":" 21/04/1978 "," Beruf ":" Entwickler "

Reguläre Ausdrücke

Ich bin mir sicher, dass Sie damit nicht zufrieden sein werden. Ich habe Ihnen etwas mehr Komplexität und erweiterte Funktionalität versprochen. Lassen Sie uns also einige reguläre Ausdrücke verwenden. Nehmen wir an, wir möchten die Benutzer suchen, die einen Vornamen haben, der mit "ma" oder "bis" beginnt, und dessen Nachnamen mit "se" oder "de" beginnen. Wie machen wir das??

Sehen Sie sich die folgende Abfrage mit einem regulären Ausdruck an:

 db.nettuts.find ("first": / (ma | bis) * / i, "last": / (se | de) / i);

In Anbetracht dessen werden die Ergebnisse sein:

 "_id": ObjectId ("4ef22e522893ba6797bf8cb6"), "first": "matthew", "last": "setter", "dob": "21/04/1978", "gender": "m", "hair_colour" ":" braun "," beruf ":" entwickler "," nationalität ":" australian " " _id ": ObjectId (" 4ef22e532893ba6797bf8cbc ")," erster ":" judi "," letzter ":" dench ", "dob": "09/12/1934", "gender": "f", "hair_colour": "weiß", "beruf": "schauspielerin", "nationalität": "englisch"

Sehen wir uns diese Frage etwas genauer an. Erstens führen wir einen Regex zum Vornamen durch.

 "first": / (ma | bis) * / i

//ich zeigt an, dass wir einen Regex mit Groß- und Kleinschreibung ausführen.

(ma | bis) * gibt an, dass der Anfang des ersten Namensstrings entweder 'ma' oder 'to' sein muss.

Wenn Sie nicht vertraut sind, stimmt das * am Ende mit irgendetwas überein. Wenn Sie es also zusammenstellen, stimmen wir mit Vornamen überein, die am Anfang entweder 'ma' oder 'to' haben. In der Regex für den Nachnamen können Sie sehen, dass wir dasselbe getan haben, aber für den Nachnamen.

Nicht ganz sicher? Lass uns noch einen versuchen. Wie wäre es mit einem der bedingten Operatoren zu kombinieren? Nehmen wir an, wir möchten alle Personen mit dem Vornamen James oder Jamie finden, die amerikanische Schauspielerinnen sind. Wie machen wir das? Nun, lass uns sehen, wie wir es unten machen würden:

 db.nettuts.find ("first": / (jam? e *) * / i, "gender": "f", "occup": "actor", "nationality": "american");

Der Regex oben entspricht Kombinationen wie: james, jamie, jamee usw. Das Fragezeichen entspricht einem Zeichen (a-z, A-Z oder 0-9). Dann entspricht das * nach wie vor allem anderen, was nach dem 'e' kommt. Von da an verwenden wir die bedingten Operatoren von vorher, um die zurückkommenden Ergebnisse weiter einzuschränken. Es wird darauf hingewiesen, dass die Abfragen keinen Index verwenden, da wir den Operator verwenden, bei dem die Groß- / Kleinschreibung nicht berücksichtigt wird. Aber für die Zwecke dieses Beispiels ist es in Ordnung.

Die Ausgabe der obigen Abfrage lautet:

 "_id": ObjectId ("4ef22e522893ba6797bf8cba"), "first": "jamie lee", "last": "curtis", "dob": "22/11/1958", "gender": "f", " hair_colour ":" braun "," beruf ":" schauspieler "," nationalität ":" amerikanisch "

Karte verkleinern

MapReduce ist der große Vater der Datenanalyse. Falls Sie noch nie davon gehört haben, ist MapReduce ein Prozess, bei dem die Aggregation von Daten in einem Computercluster aufgeteilt und verwaltet werden kann, um die Zeit zu verkürzen, die zur Ermittlung eines Aggregatergebnisses für einen Datensatz benötigt wird.

Es besteht aus zwei Teilen: Karte und Reduzieren. Map erstellt die Jobs, die dann an die Arbeiterknoten weitergeleitet werden können, um die Reduce-Komponente auszuführen. Reduce berechnet dann die Antwort für den Teil der Arbeit, die an ihn weitergegeben wurde, und gibt das Ergebnis zurück, das mit den anderen Abschnitten kombiniert werden kann, um die endgültige Antwort zu bilden.

Wenn Sie eine genauere Beschreibung wünschen, finden Sie hier folgende Informationen von Wikipedia:

MapReduce ist ein Framework für die Verarbeitung hochverteilbarer Probleme über große Datensätze hinweg, wobei eine große Anzahl von Computern (Knoten) verwendet wird, die zusammen als Cluster (wenn alle Knoten dieselbe Hardware verwenden) oder ein Grid (wenn die Knoten unterschiedliche Hardware verwenden) verwendet werden. Die Datenverarbeitung kann mit Daten erfolgen, die entweder in einem Dateisystem (unstrukturiert) oder in einer Datenbank (strukturiert) gespeichert sind..

"Karte" Schritt: Der Master-Knoten nimmt die Eingabe auf, partitioniert sie in kleinere Unterprobleme und verteilt sie an Worker-Knoten. Ein Worker-Knoten kann dies wiederum wiederholen, was zu einer mehrstufigen Baumstruktur führt. Der Arbeiterknoten verarbeitet das kleinere Problem und gibt die Antwort an seinen Master-Knoten zurück.

"Reduzieren" Schritt: Der Master-Knoten sammelt dann die Antworten auf alle Teilprobleme und kombiniert sie auf irgendeine Weise, um die Ausgabe zu bilden - die Antwort auf das Problem, das ursprünglich versucht wurde, zu lösen.

Beispiel MapReduce

Schauen wir uns ein einfaches Beispiel an. Wir werden unseren einfachen Datensatz analysieren und die Gesamtzahl aller Frauen in der Gruppe ermitteln. Dies ist zwar ein sehr simpeles Beispiel, aber es wird die Grundlage dafür legen, praktisch zu verstehen, wie MapReduce funktioniert.

Die Kartenfunktion

Hier erstellen wir eine Kartenfunktion, die die Informationen in unserem Datensatz nach dem Geschlecht der Person zusammenfasst und für jeden von ihnen eine Zahl von 1 ausgibt.

 var map = function () emit (gender: this.gender, count: 1); 

Dadurch wird eine Ausgabe ähnlich der folgenden ausgegeben:

 'f': 1

Die Reduzierfunktion

Unsere Reduzierungsfunktion nimmt die Ausgabe der Kartenfunktion und verwendet sie, um eine laufende Summe der Zählung für jedes Geschlecht zu erhalten. Schauen Sie sich unten die Reduzierfunktion an.

 var verkleinern = Funktion (Schlüssel, Werte) var result = count: 0; values.forEach (function (value) result.count + = value.count;) gibt das Ergebnis zurück; 

MapReduce ausführen

Jetzt setzen wir sie zusammen, indem wir das nennen Karte verkleinern Funktion in unserer aktuellen Datenbank. Wir passieren in der Karte und reduzieren Variablen, die wir zuvor erstellt haben, indem wir unsere aufrufen Karte und reduzieren Funktionen und geben Sie den Namen der Sammlung an, in der das Ergebnis gespeichert wird; in diesem Fall 'Geschlecht'. Um es noch einmal zu wiederholen, das Ergebnis des Aufrufs der mapReduce-Funktion ist eine Sammlung in unserer aktuellen Datenbank. dass wir iterieren können, so wie wir es auch bei jeder anderen Sammlung tun würden. Schauen Sie sich den Code unten an:

 var res = db.nettuts.mapReduce (map, verkleinern, out: 'gender');

Anzeige der Ausgabe

Wenn die Kartenverkleinerung abgeschlossen ist, können Sie wie eine normale Sammlung darauf zugreifen, indem Sie die findenFunktion wie unten.

 db.gender.find (); "_id": "gender": "f", "value": "count": 2 "_id": "gender": "m", "value": "count" : 5

Hier haben wir jetzt eine laufende Summe pro Geschlecht; 2 für Frauen und 5 für Männer - was mit unserem Datensatz korreliert. Was wäre, wenn wir nach Frauen in der Gruppe filtern wollten. Nun, nicht viel dazu. Wir müssen nur die Abfrageklausel verwenden, um dies zu ermöglichen. Glück für uns wird es bekannt aussehen. Schauen Sie sich die nachstehende Abfrage an.

 var res = db.nettuts.mapReduce (map, verkleinern, out: 'gender', Abfrage: "gender": "f");

Wenn wir nun die Ausgabe anzeigen, wird sie wie folgt aussehen:

 db.gender.find (); "_id": "gender": "f", "value": "count": 2

Es gibt eine Reihe weiterer Parameter, die Sie an die mapReduce-Funktion übergeben können, um die Ausgabe weiter anzupassen.

  • Sortieren - sortiere die zurückgegebene Ausgabe
  • Grenze - Begrenzen Sie die Anzahl der zurückgegebenen Ergebnisse
  • aus - Der Name der Sammlung, in der die Ergebnisse gespeichert werden sollen
  • abschließen - Geben Sie eine Funktion an, die nach Abschluss des Reduzierungsvorgangs ausgeführt werden soll
  • Umfang - Geben Sie Variablen an, die in der Karte verwendet werden können, und reduzieren Sie den Funktionsumfang
  • jsMode - Vermeidet einen Zwischenschritt (zwischen map und verkleinern) der Konvertierung in das JSON-Format
  • verbose - Statistiken über den Ausführungsprozess verfolgen

Auflösung

Dies war eine Wirbelwind-Berichterstattung über einige der komplexeren Themen von MongoDB. Aber ich hoffe, dass es Ihnen einen Vorgeschmack darauf gibt, was mit diesem großartigen Werkzeug möglich ist.

Wir haben uns die bedingten Operatoren angesehen: $ lt, $ gt, $ lte, $ gte, $ in, $ nin, $ nicht und führen Sie eine Einführung in MapReduce durch. Ich hoffe, dass Sie eine Menge davon mitbekommen haben und mehr über das großartige Tool, das mongoDB ist, erfahren.