559 Stimmen

Objekte zwischen zwei Daten suchen MongoDB

Ich habe herumgespielt Speichern von Tweets in Mongodb, jedes Objekt sieht wie folgt aus:

{
"_id" : ObjectId("4c02c58de500fe1be1000005"),
"contributors" : null,
"text" : "Hello world",
"user" : {
    "following" : null,
    "followers_count" : 5,
    "utc_offset" : null,
    "location" : "",
    "profile_text_color" : "000000",
    "friends_count" : 11,
    "profile_link_color" : "0000ff",
    "verified" : false,
    "protected" : false,
    "url" : null,
    "contributors_enabled" : false,
    "created_at" : "Sun May 30 18:47:06 +0000 2010",
    "geo_enabled" : false,
    "profile_sidebar_border_color" : "87bc44",
    "statuses_count" : 13,
    "favourites_count" : 0,
    "description" : "",
    "notifications" : null,
    "profile_background_tile" : false,
    "lang" : "en",
    "id" : 149978111,
    "time_zone" : null,
    "profile_sidebar_fill_color" : "e0ff92"
},
"geo" : null,
"coordinates" : null,
"in_reply_to_user_id" : 149183152,
"place" : null,
"created_at" : "Sun May 30 20:07:35 +0000 2010",
"source" : "web",
"in_reply_to_status_id" : {
    "floatApprox" : 15061797850
},
"truncated" : false,
"favorited" : false,
"id" : {
    "floatApprox" : 15061838001
}

Wie würde ich eine Abfrage schreiben, die die erstellt_am und findet alle Objekte zwischen 18:47 und 19:00? Muss ich meine Dokumente aktualisieren, damit die Datumsangaben in einem bestimmten Format gespeichert werden?

0 Stimmen

Sie sagen nicht, über welches Feld Sie eine Abfrage wünschen?

1 Stimmen

Ups, ich möchte das created_at abfragen und alles zwischen zwei Daten finden.

0 Stimmen

Ich bin neugierig, dass, warum nicht verwenden Sie Zeitstempel, alle Vorteile durch die Verwendung des Date Obj?

840voto

ponzao Punkte 19914

Abfrage nach einem Datumsbereich (bestimmter Monat oder Tag) dans le MongoDB-Kochbuch hat eine sehr gute Erklärung zu diesem Thema, aber unten ist etwas, das ich selbst ausprobiert habe und das zu funktionieren scheint.

items.save({
    name: "example",
    created_at: ISODate("2010-04-30T00:00:00.000Z")
})
items.find({
    created_at: {
        $gte: ISODate("2010-04-29T00:00:00.000Z"),
        $lt: ISODate("2010-05-01T00:00:00.000Z")
    }
})
=> { "_id" : ObjectId("4c0791e2b9ec877893f3363b"), "name" : "example", "created_at" : "Sun May 30 2010 00:00:00 GMT+0300 (EEST)" }

Meinen Experimenten zufolge müssen Sie Ihre Daten in ein Format serialisieren, das von MongoDB unterstützt wird, da die folgende Variante unerwünschte Suchergebnisse liefert.

items.save({
    name: "example",
    created_at: "Sun May 30 18.49:00 +0000 2010"
})
items.find({
    created_at: {
        $gte:"Mon May 30 18:47:00 +0000 2015",
        $lt: "Sun May 30 20:40:36 +0000 2010"
    }
})
=> { "_id" : ObjectId("4c079123b9ec877893f33638"), "name" : "example", "created_at" : "Sun May 30 18.49:00 +0000 2010" }

Im zweiten Beispiel wurden keine Ergebnisse erwartet, aber es wurde dennoch eines erzielt. Das liegt daran, dass ein einfacher String-Vergleich durchgeführt wird.

3 Stimmen

Sieht interessant aus, aber muss das gespeicherte Datum ein bestimmtes Format haben? Ich habe nur gespeichert, was von Twitter zur Verfügung gestellt wurde, muss dies in ein anderes Format geändert werden?

9 Stimmen

Wahrscheinlich haben Sie die Zeitstempel als Strings gespeichert, so dass MongoDB vermutlich nicht erkennt, dass es sich um Datumsangaben handelt. Daher würde eine Bereichsabfrage für sie zu einer alphabetischen Bereichsabfrage führen (z. B. "Jan Mon 01.01.2010" liegt vor "Jan Sun 01.01.1000"). Es wäre wahrscheinlich sinnvoll, alle Datumsdaten in das MongoDB-Format zu formatieren, die ich denke, ist nur plain JavaScript Date.

2 Stimmen

Ich habe gerade dies verwendet, um meine Strings in Datumsobjekte zu konvertieren stackoverflow.com/questions/2900674/

50voto

arcseldon Punkte 32403

Zur Klarstellung. Es ist wichtig zu wissen, dass:

  • Ja, Sie müssen ein Javascript-Date-Objekt übergeben.
  • Ja, es muss ISODate-freundlich sein
  • Ja, meiner Erfahrung nach müssen Sie das Datum in ISO umwandeln, damit dies funktioniert.
  • Ja, die Arbeit mit Daten ist im Allgemeinen immer ein mühsamer Prozess, und Mongo ist da keine Ausnahme.

Hier ist ein Arbeitsschnipsel des Codes, wo wir ein wenig Datum Manipulation tun, um sicherzustellen, dass Mongo (hier bin ich mit Mongoose-Modul und wollen Ergebnisse für Zeilen, deren Datum-Attribut kleiner ist als (vor) das Datum als myDate-Param gegeben) kann es richtig behandeln:

var inputDate = new Date(myDate.toISOString());
MyModel.find({
    'date': { $lte: inputDate }
})

1 Stimmen

Plus eine zur Verdeutlichung. Wenn Sie moment im Backend verwenden, wird die Funktion toISOString() beibehalten. Ich verwende Moment, um Zeit für meine Abfragen zu addieren und zu subtrahieren.

31voto

Anton Tarasenko Punkte 7355

Python und pymongo

Suche nach Objekten zwischen zwei Daten in Python mit pymongo in Sammlung posts (basierend auf dem Lehrgang ):

from_date = datetime.datetime(2010, 12, 31, 12, 30, 30, 125000)
to_date = datetime.datetime(2011, 12, 31, 12, 30, 30, 125000)

for post in posts.find({"date": {"$gte": from_date, "$lt": to_date}}):
    print(post)

Wo {"$gte": from_date, "$lt": to_date} spezifiziert den Bereich in Form von datetime.datetime Typen.

1 Stimmen

Das funktioniert nicht. Immer wenn ich diese Abfrage ausführe, erhalte ich standardmäßig eine vollständige Antwort und keine gefilterte Antwort

2 Stimmen

Das funktioniert nicht. Ich habe es mit python3 versucht und erhalte keine Ergebnisse zurück

23voto

GSK Punkte 523
db.collection.find({"createdDate":{$gte:new ISODate("2017-04-14T23:59:59Z"),$lte:new ISODate("2017-04-15T23:59:59Z")}}).count();

Ersetzen Sie collection mit dem Namen der Sammlung, die Sie abfragen möchten

2 Stimmen

@DanDascalescu - es mag sein, dass es nichts gebracht hat, aber was ist Ihr Anliegen hier?

33 Stimmen

Doppelte Antworten verschwenden die Zeit anderer.

1 Stimmen

@DanDascalescu - dann vergeuden Sie keine Zeit, tun Sie etwas Produktives.

21voto

Ben Smith Punkte 1484

MongoDB speichert die Millisekunden eines Datums als int(64), wie es in http://bsonspec.org/#/specification

Es kann jedoch ziemlich verwirrend werden, wenn Sie Daten abrufen, da der Client-Treiber ein Datumsobjekt mit seiner eigenen lokalen Zeitzone instanziiert. Der JavaScript-Treiber in der Mongo-Konsole wird dies sicherlich tun.

Wenn Sie sich also um Ihre Zeitzonen kümmern, sollten Sie wissen, wie die Zeitzone sein soll, wenn Sie sie zurückbekommen. Das sollte für die Abfragen nicht so wichtig sein, da es immer noch demselben int(64) entspricht, unabhängig davon, in welcher Zeitzone sich Ihr Datumsobjekt befindet (hoffe ich). Aber ich würde auf jeden Fall Abfragen mit tatsächlichen Datum Objekte (nicht Zeichenfolgen) und lassen Sie den Treiber sein Ding tun.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X