日韩av黄I国产麻豆传媒I国产91av视频在线观看I日韩一区二区三区在线看I美女国产在线I麻豆视频国产在线观看I成人黄色短片

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

mongo数据库CRUD

發布時間:2025/3/17 数据库 42 豆豆
生活随笔 收集整理的這篇文章主要介紹了 mongo数据库CRUD 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

#準備

從官網下載合適的安裝包。這里以win10為例,一路next即可完成安裝。安裝完成后,進入這個目錄:

C:\Program Files\MongoDB\Server\4.0\bin\

在當前目錄打開PowerShell窗口,先啟動服務端:

.\mongod.exe

服務端默認在本地的27017端口運行。

啟動客戶端:

.\mongo.exe

將默認連接本地27017端口的服務端,并啟動mongo shell交互式命令行窗口。

如果想指定端口或者連接遠程的服務,可以在啟動時指定其他參數,比如:

.\mongo.exe --host www.example.com --port 28015

顯示當前使用的數據庫:

db # 默認數據庫是test

切換數據庫:

use <database>

你也可以切換到一個不存在的數據庫。因為當你往其中插入數據時,mongo將自動創建這個數據庫(或者集合),比如:

> use first switched to db first > db.test_coll.insertOne({x:1}) {"acknowledged" : true,"insertedId" : ObjectId("5c52cdf38410c398987c5c0e") }

上述的insertOne()操作將同時創建數據庫first和集合test_coll。

PyMongo

連接和指定數據庫

PyMongo是mongo的python驅動,安裝好之后我們連接MongoDB

方式一:指定主機和端口

import pymongo client = pymongo.MongoClient(host='localhost', port=27017)

方式二:mongodb連接字符串

client = pymongo.MongoClient('mongodb://localhost:27017/') db = db.test # 默認數據庫是test

插入數據

數據庫

默認數據庫是test,我們也可以指定其他數據庫,比如school

client = pymongo.MongoClient('mongodb://localhost:27017/') db = client.school # 或者 db = client['school']

注意,可以直接連接一個不存在的數據庫。mongo會在需要時(比如插入數據),創建這個數據庫。

集合

mongo中的集合(collection),類似于SQL中的表(table)。指定集合的操作,與指定數據庫的方式類似:

collection = db.teacher # 或者 collection = db['teacher']

注意,可以指定一個不存在的集合。mongo會在需要時(比如插入數據),創建這個集合。

文檔

MongoDB將數據存儲為BSON文檔(BSON是JSON文檔的二進制表示,但是包含更多的數據類型)。文檔由字段(field)和值(value)組成,具有如下結構:

{field1: value1,field2: value2,field3: value3,...fieldN: valueN }

字段名是字符串,具有如下約束條件:

  • _id是保留字段,用作主鍵,必須保證唯一且不可以變(因此不能是數組)
  • 字段名不可包含null字符
  • 不要以$或.開頭
  • 字段名不可重復

在PyMongo中,使用python的字典表示文檔,例如下面字典可以用來表示一篇博文:

>>> import datetime >>> post = {"author": "Mike", ... "text": "My first blog post!", ... "tags": ["mongodb", "python", "pymongo"], ... "date": datetime.datetime.utcnow()}

值得注意的是,文檔可以包含python中的原生類型(比如datetime.datetime實例),PyMongo會將其自動轉化為合適的BSON類型。

MongoDB使用.點來訪問數組或嵌套文檔中的元素:

{...contribs: [ "Turing machine", "Turing test", "Turingery" ],... }

如果要訪問contribs字段的第三個元素,使用contribs.2

{...name: { first: "Alan", last: "Turing" },contact: { phone: { type: "cell", number: "111-222-3333" } },... }

如果要訪問name字段的last字段,使用name.last

文檔的限制

  • BSON文檔的最大大小是16MB
  • 字段的順序:MongoDB保持寫操作時的字段順序,除了以下情況:
    • _id字段總是文檔的第一個字段
    • 重新命名字段等更新操作可能影響字段排序
  • _id字段:
    • 如果插入文檔沒有指定_id字段,MongoDB會自動創建ObjectId對象作為該字段的值
    • 創建集合(collection)時,MongoDB默認為該字段創建唯一索引
    • 該字段的值通常是:
      • ObjectId
      • 自增數字
      • 代碼生成的UUID

插入數據

MongoDB的所有寫操作,在當個文檔上是原子性的。插入文檔時,如果集合不存在,MongoDB會自動創建。

db.collection.insert()

下面我們往teacher這個集合中插入一條數據

# 數據用字典結構 teacher = {'name': 'Sven','gender': 'male','major': 'Math' }# 插入成功后,返回該條數據的 _id res = db.teacher.insert(teacher) # 5c53c429bddaf0ac186d935b

插入多條數據

teacher1 = {'name': 'Sylvia','gender': 'female','major': 'Deutsch' }teacher2 = {'name': 'Lolle','gender': 'female','major': 'Geschichte' }res = db.teacher.insert([teacher1, teacher2]) # 返回_id的列表 # [ObjectId('5c53c628bddaf0b2bc028a73'), ObjectId('5c53c628bddaf0b2bc028a74')]

以上我們插入單條和多條都用insert方法,更推薦的方式是使用insert_one()和insert_many()

db.collection.insert_one()

插入單條數據

res = db.inventory.insert_one({"item": "canvas","qty": 100,"tags": ["cotton"],"size": {"h": 28, "w": 35.5, "uom": "cm"}})print(res) # <pymongo.results.InsertOneResult object at 0x0332EF58> print(res.inserted_id) # 5c53c7a8bddaf0208cd858f5

db.collection.insert_many()

插入多條數據

res = db.inventory.insert_many([{"item": "journal","qty": 25,"tags": ["blank", "red"],"size": {"h": 14, "w": 21, "uom": "cm"}},{"item": "mat","qty": 85,"tags": ["gray"],"size": {"h": 27.9, "w": 35.5, "uom": "cm"}},{"item": "mousepad","qty": 25,"tags": ["gel", "blue"],"size": {"h": 19, "w": 22.85, "uom": "cm"}}])print(res) # <pymongo.results.InsertManyResult object at 0x031C3F30> print(res.inserted_ids) # [ObjectId('5c53e48bbddaf04c44880d70'), ObjectId('5c53e48bbddaf04c44880d71'), ObjectId('5c53e48bbddaf04c44880d72')]

插入數據時,如果指定_id的值,那么該值不能和集合中已有文檔的_id重復。

查詢數據

查詢使用db.collection.find()方法。

首先,準備一些原始數據

import pymongoclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test1db.inventory.insert_many([{"item": "journal","qty": 25,"size": {"h": 14, "w": 21, "uom": "cm"},"status": "A"},{"item": "notebook","qty": 50,"size": {"h": 8.5, "w": 11, "uom": "in"},"status": "A"},{"item": "paper","qty": 100,"size": {"h": 8.5, "w": 11, "uom": "in"},"status": "D"},{"item": "planner","qty": 75, "size": {"h": 22.85, "w": 30, "uom": "cm"},"status": "D"},{"item": "postcard","qty": 45,"size": {"h": 10, "w": 15.25, "uom": "cm"},"status": "A"}])

查詢集合中的所有文檔:find()

傳入一個空文檔作為find的查詢條件即可

cursor = db.inventory.find({})

以上操作相當于SQL中的:

SELECT * FROM inventory

find方法返回一個Cursor實例,遍歷它即可訪問所有文檔:

docs = [doc for doc in cursor] """ [{'status': 'A', 'item': 'journal', ...}, ...] """

查詢單個文檔:find_one()

find_one()方法返回滿足查詢條件的一個文檔,或者返回None(如果沒有匹配的結果)。適用于:

  • 你知道有且只有一個匹配的文檔,比如通過ObjectId進行查詢
  • 你只需要第一個匹配的文檔

根據ObjectID對象查詢

注意,ObjectId對象和它的字符串表現是完全不同的,后者不可直接用于查詢

import pymongo import datetimeclient = pymongo.MongoClient(host='localhost',port=27017,retryWrites=True ) db = client.test8blog = {"author": "Ayhan","text": "My first blog post!","tags": ["mongodb", "python", "pymongo"],"date": datetime.datetime.utcnow()}post_id = db.posts.insert_one(blog).inserted_id # 返回ObjectId對象 print(post_id) # 5c948354bddaf02674a54faares1 = db.posts.find_one({'_id': post_id}) # 通過ObjectId對象查詢 print(res1) """ {'_id': ObjectId('5c948354bddaf02674a54faa'),'author': 'Ayhan','text': 'My first blog post!','tags': ['mongodb', 'python', 'pymongo'],'date': datetime.datetime(2019, 3, 22, 6, 40, 20, 164000) } """res2 = db.posts.find_one({'_id': str(post_id)}) # 通過ObjectId對象的字符串表現進行查詢 print(res2) # None

如果想通過ObjectId的字符串進行查詢,需要將字符串轉為對象:

from bson.objectid import ObjectIdobject_id_str = '5c948354bddaf02674a54faa' db.posts.find_one({'_id': ObjectId(object_id_str)})

指定相等條件

如果要指定相等條件,可以給find方法傳入文檔查詢條件:

{ <field1>: <value1>, ... }

比如,下面的示例從inventory集合中查詢所有符合status等于D的文檔:

cursor = db.inventory.find({'status': 'D'})

上述操作相當于SQL中的

SELECT * FROM inventory WHERE status = "D"

使用查詢運算符

文檔查詢條件:

{ <field1>: { <operator1>: <value1> }, ... }

下面的示例從inventory集合中查詢所有status等于A或D的文檔:

cursor = db.inventory.find({'status': {'$in': ['A', 'D']}})

以上查詢相當于SQL中的:

SELECT * FROM inventory WHERE status in ("A", "D")

查詢運算符一覽,可查看官方文檔:https://docs.mongodb.com/manual/reference/operator/query/#projection-operators

AND查詢

復合查詢可以指定多個字段。下面的示例從inventory集合中查詢所有status等于A,并且qty小于30的文檔:

cursor = db.inventory.find({'status': 'A', 'qty': {'$lt': 30}})

以上操作相當于SQL中的:

SELECT * FROM inventory WHERE status = "A" AND qty < 30

OR查詢

使用$or運算符,可以進行邏輯或查詢:

cursor = db.inventory.find({'$or': [{'status': 'A'}, {'qty': {'$lt': 30}}]} )

以上操作相當于SQL中的:

SELECT * FROM inventory WHERE status = "A" OR qty < 3

AND 和 OR 查詢

cursor = db.inventory.find({'status': 'A','$or': [{'qty': {'$lt': 30}}, {'item': {'$regex': '^p'}}] })

以上操作相當于SQL中的:

SELECT * FROM inventory WHERE status = "A" AND ( qty < 30 OR item LIKE "p%")

嵌套查詢

適用于文檔中嵌套文檔的查詢。下面先填充數據:

import pymongo from bson.son import SONclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test2db.inventory.insert_many([{"item": "journal","qty": 25,"size": SON([("h", 14), ("w", 21), ("uom", "cm")]),"status": "A"},{"item": "notebook","qty": 50,"size": SON([("h", 8.5), ("w", 11), ("uom", "in")]),"status": "A"},{"item": "paper","qty": 100,"size": SON([("h", 8.5), ("w", 11), ("uom", "in")]),"status": "D"},{"item": "planner","qty": 75,"size": SON([("h", 22.85), ("w", 30), ("uom", "cm")]),"status": "D"},{"item": "postcard","qty": 45,"size": SON([("h", 10), ("w", 15.25), ("uom", "cm")]),"status": "A"}])

注意,子文檔鍵的順序在這些示例中很重要,因此這里的子文檔使用bson.son.SON的實例,而不是使用python的字典形式。

插入后,數據結構如下:

[{ // 文檔"_id" : ObjectId("5c540556bddaf0b00803d342"),"status" : "A","item" : "journal","size" : { // 子文檔(嵌套文檔)"h" : 14,"w" : 21,"uom" : "cm"},"qty" : 25} ]

根據子文檔進行查詢

如果某個字段是一個子文檔,要為該字段指定相等條件時,使用如下文檔查詢條件:{ <field>: <value> },其中<value>是作為匹配條件的子文檔。

下面的示例從inventory集合中查詢size字段等于子文檔{ h: 14, w:21, uom: "cm" }的文檔

cursor = db.inventory.find({'size': SON([("h", 14), ("w", 21), ("uom", "cm")])} ) """ [{u 'status': u 'A',u 'item': u 'journal',u '_id': ObjectId('5c540556bddaf0b00803d342'),u 'qty': 25,u 'size': {u 'h': 14,u 'uom': u 'cm',u 'w': 21} }] """

注意:

根據子文檔進行查詢時,子文檔必須完全匹配,包括字段的順序。也就也是說,下面的查詢無法匹配任何結果:

cursor = db.inventory.find({"size": SON([("w", 21), ("h", 14), ("uom", "cm")])} ) # []

根據嵌套字段進行查詢

通過子文檔的字段進行查詢,需要使用.操作:field.nestedField

# 查詢 size.uom 等于 in 的文檔 cursor = db.inventory.find({'size.uom': 'in'} ) """ [{u 'status': u 'A',u 'item': u 'notebook',u '_id': ObjectId('5c540556bddaf0b00803d343'),u 'qty': 50,u 'size': {u 'h': 8.5,u 'uom': u 'in',u 'w': 11} }, {u 'status': u 'D',u 'item': u 'paper',u '_id': ObjectId('5c540556bddaf0b00803d344'),u 'qty': 100,u 'size': {u 'h': 8.5,u 'uom': u 'in',u 'w': 11} }] """ # 查詢 size.h 小于 10 的文檔 cursor = db.inventory.find({'size.h': {'$lt': 10}} ) """ [{u 'status': u 'A',u 'item': u 'notebook',u '_id': ObjectId('5c540556bddaf0b00803d343'),u 'qty': 50,u 'size': {u 'h': 8.5,u 'uom': u 'in',u 'w': 11} }, {u 'status': u 'D',u 'item': u 'paper',u '_id': ObjectId('5c540556bddaf0b00803d344'),u 'qty': 100,u 'size': {u 'h': 8.5,u 'uom': u 'in',u 'w': 11} }] """ # 查詢 size.h 小于 15,size.uom 等于 in, 并且status 等于D的文檔 cursor = db.inventory.find({'size.h': {'$lt': 15}, 'size.uom': 'in', 'status': 'D'} ) """ [{u 'status': u 'D',u 'item': u 'paper',u '_id': ObjectId('5c540556bddaf0b00803d344'),u 'qty': 100,u 'size': {u 'h': 8.5,u 'uom': u 'in',u 'w': 11} }] """

數組查詢

首先準備數據:

import pymongoclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test3db.inventory.insert_many([{"item": "journal","qty": 25,"tags": ["blank", "red"],"dim_cm": [14, 21]},{"item": "notebook","qty": 50,"tags": ["red", "blank"],"dim_cm": [14, 21]},{"item": "paper","qty": 100,"tags": ["red", "blank", "plain"],"dim_cm": [14, 21]},{"item": "planner","qty": 75,"tags": ["blank", "red"],"dim_cm": [22.85, 30]},{"item": "postcard","qty": 45,"tags": ["blue"],"dim_cm": [10, 15.25]},{"item": "mac","qty": 12,"tags": ["silver", "golden"],"dim_cm": [25, 34]} ])

查詢整個數組

根據數組指定相等條件時,使用文檔查詢條件:{ <field>: <value> },其中<value>就是要進行匹配的數組本身,包括其中元素的順序。

# 查詢tags字段的值等于['red', 'blank']的文檔 cursor = db.inventory.find({'tags': ['red', 'blank']} ) """ [{u 'item': u 'notebook',u '_id': ObjectId('5c54138fbddaf0a1e075f0ff'),u 'qty': 50,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank'] }] """

當然,如果你希望查詢數組中包含red和blank元素(不關心元素順序,或者是否有多余元素)的所有文檔,可以使用$all操作符:

cursor = db.inventory.find({'tags': {'$all': ['red', 'blank']}} ) """ [{u 'item': u 'journal',u '_id': ObjectId('5c54138fbddaf0a1e075f0fe'),u 'qty': 25,u 'dim_cm': [14, 21],u 'tags': [u 'blank', u 'red'] }, {u 'item': u 'notebook',u '_id': ObjectId('5c54138fbddaf0a1e075f0ff'),u 'qty': 50,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank'] }, {u 'item': u 'paper',u '_id': ObjectId('5c54138fbddaf0a1e075f100'),u 'qty': 100,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank', u 'plain'] }, {u 'item': u 'planner',u '_id': ObjectId('5c54138fbddaf0a1e075f101'),u 'qty': 75,u 'dim_cm': [22.85, 30],u 'tags': [u 'blank', u 'red'] }] """

查詢數組中的某個元素(指定單個查詢條件)

查詢數組中包含某個元素的文檔時,使用{ <field>: <value> },其中<value>是數組中的元素

# 查詢tags中包含red的文檔 cursor = db.inventory.find({'tags': 'red'} ) """ [{u 'item': u 'journal',u '_id': ObjectId('5c54138fbddaf0a1e075f0fe'),u 'qty': 25,u 'dim_cm': [14, 21],u 'tags': [u 'blank', u 'red'] }, {u 'item': u 'notebook',u '_id': ObjectId('5c54138fbddaf0a1e075f0ff'),u 'qty': 50,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank'] }, {u 'item': u 'paper',u '_id': ObjectId('5c54138fbddaf0a1e075f100'),u 'qty': 100,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank', u 'plain'] }, {u 'item': u 'planner',u '_id': ObjectId('5c54138fbddaf0a1e075f101'),u 'qty': 75,u 'dim_cm': [22.85, 30],u 'tags': [u 'blank', u 'red'] }] """

如果要給數組元素指定多個條件,可以在查詢條件中使用查詢運算符:{<array filed>: {<operator1>: <value1>, ...},具體如下個部分

為數組內的元素指定多個查詢條件

當為數組內的元素指定多個條件時,你可以指定要么單個元素滿足這些條件,或者數組內元素的任意組合滿足這些條件。

# 查詢dim_cm數組中元素的組合滿足查詢條件: # 一個元素大于15,另一個元素小于20,或者一個元素滿足兩種條件的的文檔 cursor = db.inventory.find({'dim_cm': {'$gt': 15, '$lt': 20}} ) """ [{u 'item': u 'journal',u '_id': ObjectId('5c54138fbddaf0a1e075f0fe'),u 'qty': 25,u 'dim_cm': [14, 21],u 'tags': [u 'blank', u 'red'] }, {u 'item': u 'notebook',u '_id': ObjectId('5c54138fbddaf0a1e075f0ff'),u 'qty': 50,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank'] }, {u 'item': u 'paper',u '_id': ObjectId('5c54138fbddaf0a1e075f100'),u 'qty': 100,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank', u 'plain'] }, {u 'item': u 'postcard',u '_id': ObjectId('5c54138fbddaf0a1e075f102'),u 'qty': 45,u 'dim_cm': [10, 15.25],u 'tags': [u 'blue'] }] 注意:"dim_cm": [25, 34]的元素并不會被過濾出來。 """
一個數組元素同時滿足多個條件

使用$elemMatch運算符,指定多個條件,只要有1個元素同時滿足這些條件即可。

# 查詢dim_cm數組中,至少有一個大于15且小于20的元素的文檔 cursor = db.inventory.find({'dim_cm': {'$elemMatch': {'$gt': 15, '$lt': 20}}} ) """ [{u 'item': u 'postcard',u '_id': ObjectId('5c8ba39bbddaf00ea0365693'),u 'qty': 45,u 'dim_cm': [10, 15.25],u 'tags': [u 'blue'] }] 15.25 滿足既大于15,又小于20的條件 """
元素的組合滿足復合查詢條件
# 查詢dim_cm數組中元素的組合滿足查詢條件: # 存在某些元素大于15,且某些元素小于20,或者一個元素滿足兩種條件的的文檔 # (若instock下的所有元素的組合都不能滿足以上條件,則無法被過濾出來) # 注意:"dim_cm": [25, 34]的元素并不會被過濾出來。 cursor = db.inventory.find({'dim_cm': {'$gt': 15, '$lt': 20}} ) """ [{u 'item': u 'journal',u '_id': ObjectId('5c54138fbddaf0a1e075f0fe'),u 'qty': 25,u 'dim_cm': [14, 21],u 'tags': [u 'blank', u 'red'] }, {u 'item': u 'notebook',u '_id': ObjectId('5c54138fbddaf0a1e075f0ff'),u 'qty': 50,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank'] }, {u 'item': u 'paper',u '_id': ObjectId('5c54138fbddaf0a1e075f100'),u 'qty': 100,u 'dim_cm': [14, 21],u 'tags': [u 'red', u 'blank', u 'plain'] }, {u 'item': u 'postcard',u '_id': ObjectId('5c54138fbddaf0a1e075f102'),u 'qty': 45,u 'dim_cm': [10, 15.25],u 'tags': [u 'blue'] }] """
通過數組的索引查詢元素

使用.點,根據數組中指定索引的元素進行查詢。索引從0開始。

# 根據dim_cm數組的第一個元素,滿足大于20,且小于25進行查詢 cursor = db.inventory.find({'dim_cm.0': {'$gt': 20, '$lt': 25}} ) """ [{u 'item': u 'planner',u '_id': ObjectId('5c8ba39bbddaf00ea0365692'),u 'qty': 75,u 'dim_cm': [22.85, 30],u 'tags': [u 'blank', u 'red'] }] """

包含子文檔的數組

準備數據:

import pymongo from bson.son import SONclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test4db.inventory.insert_many([{"item": "journal","instock": [SON([("warehouse", "A"), ("qty", 5)]),SON([("warehouse", "C"), ("qty", 15)])]},{"item": "notebook","instock": [SON([("warehouse", "C"), ("qty", 5)])]},{"item": "paper","instock": [SON([("warehouse", "A"), ("qty", 60)]),SON([("warehouse", "B"), ("qty", 15)])]},{"item": "planner","instock": [SON([("warehouse", "A"), ("qty", 40)]),SON([("warehouse", "B"), ("qty", 5)])]},{"item": "postcard","instock": [SON([("warehouse", "B"), ("qty", 15)]),SON([("warehouse", "C"), ("qty", 35)])]}])

根據子文檔進行匹配

# instock數組的某個元素能匹配指定的文檔 cursor = db.inventory.find({'instock': SON([('warehouse', 'A'), ('qty', 5)]) })""" [{u 'item': u 'journal',u '_id': ObjectId('5c8c5f4abddaf049404c5e89'),u 'instock': [{ // 該元素能夠匹配指定的文檔條件u 'warehouse': u 'A',u 'qty': 5}, {u 'warehouse': u 'C',u 'qty': 15}] }] """

根據文檔進行匹配是嚴格匹配,包括文檔的順序,因此如下查詢無法匹配任何結果:

cursor = db.inventory.find({'instock': SON([('qty', 5), ('warehouse', 'A')]) })

對子文檔的 某個字段指定單個查詢條件

對所有子文檔內的某個字段指定一個查詢條件
# 查詢instock數組內至少包含一個子文檔,其滿足qty字段小于等于10的所有文檔 cursor = db.inventory.find({'instock.qty': {'$lte': 10} }) """ [{u 'item': u 'journal',u '_id': ObjectId('5c8c5f4abddaf049404c5e89'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 5}, {u 'warehouse': u 'C',u 'qty': 15}] }, {u 'item': u 'notebook',u '_id': ObjectId('5c8c5f4abddaf049404c5e8a'),u 'instock': [{u 'warehouse': u 'C',u 'qty': 5}] }, {u 'item': u 'planner',u '_id': ObjectId('5c8c5f4abddaf049404c5e8c'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 40}, {u 'warehouse': u 'B',u 'qty': 5}] }] """
使用數組索引來指定子文檔的某個字段進行查詢
# 查詢instock數組的第一個子文檔的qty字段滿足大于20的所有文檔 cursor = db.inventory.find({'instock.0.qty': {'$gt': 20} }) """ [{u 'item': u 'paper',u '_id': ObjectId('5c8c5f4abddaf049404c5e8b'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 60}, {u 'warehouse': u 'B',u 'qty': 15}] }, {u 'item': u 'planner',u '_id': ObjectId('5c8c5f4abddaf049404c5e8c'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 40}, {u 'warehouse': u 'B',u 'qty': 5}] }] """

對子文檔指定多個字段查詢條件

當對子文檔指定多個字段查詢條件時,你可以指定要么單個子文檔滿足這些條件,或者任意子文檔的組合滿足條件(類似上面的數組內元素指定多個條件)

單個子文檔滿足多個字段的查詢條件

使用$elemMatch運算符對包含子文檔的數組指定多個條件,至少有一個子文檔能滿足這些條件即可

# 查詢instock數組至少包含一個子文檔同時滿足qty等于5,warehouse等于4的所有文檔 cursor = db.inventory.find({'instock': {'$elemMatch': {'qty': 5, 'warehouse': 'A'}} })""" [{u 'item': u 'journal',u '_id': ObjectId('5c8c5f4abddaf049404c5e89'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 5}, {u 'warehouse': u 'C',u 'qty': 15}] }] """ # 查詢instock數組至少包含一個子文檔,其qty大于30,小于等于50的所有文檔 cursor = db.inventory.find({'instock': {'$elemMatch': {'qty': {'$gt': 30, '$lte': 50}}}} ) """ [{u 'item': u 'planner',u '_id': ObjectId('5c8c5f4abddaf049404c5e8c'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 40}, {u 'warehouse': u 'B',u 'qty': 5}] }, {u 'item': u 'postcard',u '_id': ObjectId('5c8c5f4abddaf049404c5e8d'),u 'instock': [{u 'warehouse': u 'B',u 'qty': 15}, {u 'warehouse': u 'C',u 'qty': 35}] }] """
子文檔組合滿足復合查詢條件

如果復合查詢不使用$elemMatch運算符,那么查詢將選擇那些數組包含任何能滿足條件的組合。比如:

# 查詢instock下的某些子文檔的qty字段大于30,且某些子文檔的qty字段小于等于50,(或同時滿足)的所有文檔 # (若instock下的所有文檔的組合都不能滿足以上條件,則無法被過濾出來) cursor = db.inventory.find({'instock.qty': {'$gt': 30, '$lte': 50}} ) """ [{u 'item': u 'paper',u '_id': ObjectId('5c8c5f4abddaf049404c5e8b'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 60}, {u 'warehouse': u 'B',u 'qty': 15}] }, {u 'item': u 'planner',u '_id': ObjectId('5c8c5f4abddaf049404c5e8c'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 40}, {u 'warehouse': u 'B',u 'qty': 5}] }, {u 'item': u 'postcard',u '_id': ObjectId('5c8c5f4abddaf049404c5e8d'),u 'instock': [{u 'warehouse': u 'B',u 'qty': 15}, {u 'warehouse': u 'C',u 'qty': 35}] }] """ # 查詢instock下的某些子文檔的qty字段等于5,且某些子文檔的warehouse等于A,(或同時滿足)的所有文檔 cursor = db.inventory.find({'instock.qty': 5, 'instock.warehouse': 'A' }) """ [{u 'item': u 'journal',u '_id': ObjectId('5c8c5f4abddaf049404c5e89'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 5}, {u 'warehouse': u 'C',u 'qty': 15}] }, {u 'item': u 'planner',u '_id': ObjectId('5c8c5f4abddaf049404c5e8c'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 40}, {u 'warehouse': u 'B',u 'qty': 5}] }] """

返回字段

默認情況下,MongoDB的查詢返回匹配文檔的所有字段,如果想限制返回數據的大小,可以使用projection文檔(投影文檔)來指定返回的字段。

準備數據:

import pymongoclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test5db.inventory.insert_many([{"item": "journal","status": "A","size": {"h": 14, "w": 21, "uom": "cm"},"instock": [{"warehouse": "A", "qty": 5}]},{"item": "notebook","status": "A","size": {"h": 8.5, "w": 11, "uom": "in"},"instock": [{"warehouse": "C", "qty": 5}]},{"item": "paper","status": "D","size": {"h": 8.5, "w": 11, "uom": "in"},"instock": [{"warehouse": "A", "qty": 60}]},{"item": "planner","status": "D","size": {"h": 22.85, "w": 30, "uom": "cm"},"instock": [{"warehouse": "A", "qty": 40}]},{"item": "postcard","status": "A","size": {"h": 10, "w": 15.25, "uom": "cm"},"instock": [{"warehouse": "B", "qty": 15},{"warehouse": "C", "qty": 35}]}])

我們看以下查詢:

cursor = db.inventory.find({"status": "A"})

該查詢相當于SQL的:

SELECT * FROM inventory WHERE status = 'A'

只返回指定字段和 _id 字段

在投影文檔中,將需要的字段設置為1,就可以指定查詢后返回的字段。比如:

cursor = db.inventory.find( # find的第二個參數是投影文檔{'status': 'A'}, {'item': 1, 'status': 1} )""" [{u 'status': u 'A',u 'item': u 'journal',u '_id': ObjectId('5c8ca21dbddaf046e0efdd49') }, {u 'status': u 'A',u 'item': u 'notebook',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4a') }, {u 'status': u 'A',u 'item': u 'postcard',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4d') }] """

上述查詢相當于SQL:

SELECT _id, item, status from inventory WHERE status = "A"

丟棄 _id 字段

_id字段會默認返回,如果不需要,可以在投影文檔中指定 _id: 0

cursor = db.inventory.find({'status': 'A'}, {'item': 1, 'status': 1, '_id': 0} )

返回所有字段,排除某些字段

將要排除的字段在投影文檔中設置為0即可

cursor = db.inventory.find({'status': 'A'}, {'status': 0, 'instock': 0} )""" [{u 'item': u 'journal',u '_id': ObjectId('5c8ca21dbddaf046e0efdd49'),u 'size': {u 'h': 14,u 'w': 21,u 'uom': u 'cm'} }, {u 'item': u 'notebook',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4a'),u 'size': {u 'h': 8.5,u 'w': 11,u 'uom': u 'in'} }, {u 'item': u 'postcard',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4d'),u 'size': {u 'h': 10,u 'w': 15.25,u 'uom': u 'cm'} }] """

注意

除了_id字段,projection中不能既有指定字段,又有排除字段。下面的查詢會報錯:

cursor = db.inventory.find({'status': 'A'}, {'status': 0, 'instock': 0, 'item': 1} )""" pymongo.errors.OperationFailure: Projection cannot have a mix of inclusion and exclusion. """

返回子文檔中的指定字段

通過.點標記指定嵌套字段并設置為1即可,比如

# 查詢所有文檔,并且只返回size子文檔中的uom字段 cursor = db.inventory.find({}, {'item': 1, 'status': 1, 'size.uom': 1} )""" [{u 'status': u 'A',u 'item': u 'journal',u '_id': ObjectId('5c8ca21dbddaf046e0efdd49'),u 'size': {u 'uom': u 'cm'} }, // ... {u 'status': u 'A',u 'item': u 'postcard',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4d'),u 'size': {u 'uom': u 'cm'} }] """

丟棄子文檔中的指定字段

通過.點標記指定嵌套字段并設置為0即可,比如

# 查詢satus等于D的所有文檔,且子文檔不返回uom字段 cursor = db.inventory.find({'status': 'D'}, {'size.uom': 0} )""" [{u 'status': u 'D',u 'item': u 'paper',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4b'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 60}],u 'size': {u 'h': 8.5,u 'w': 11} }, {u 'status': u 'D',u 'item': u 'planner',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4c'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 40}],u 'size': {u 'h': 22.85,u 'w': 30} }] """

投射數組內的子文檔指定字段

使用.標記來投影數組內子文檔的字段即可,比如

cursor = db.inventory.find({'status': 'D'}, {'item': 1, 'status': 1, 'instock.qty': 1} )""" [{u 'status': u 'D',u 'item': u 'paper',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4b'),u 'instock': [{u 'qty': 60}] }, {u 'status': u 'D',u 'item': u 'planner',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4c'),u 'instock': [{u 'qty': 40}] }] """

投射指定的數組元素

MongoDB為包含數組的字段提供了一些運算符,來操作數組:

$elemMatch, $slice, $

下面使用切片運算符$slice來返回數組中的最后一個元素:

cursor = db.inventory.find({'status': 'A'},{'item': 1, 'status': 1, 'instock': {'$slice': -1}} )""" [{u 'status': u 'A',u 'item': u 'journal',u '_id': ObjectId('5c8ca21dbddaf046e0efdd49'),u 'instock': [{u 'warehouse': u 'A',u 'qty': 5}] }, {u 'status': u 'A',u 'item': u 'notebook',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4a'),u 'instock': [{u 'warehouse': u 'C',u 'qty': 5}] }, {u 'status': u 'A',u 'item': u 'postcard',u '_id': ObjectId('5c8ca21dbddaf046e0efdd4d'),u 'instock': [{u 'warehouse': u 'C',u 'qty': 35}] }] """

查詢Null或缺失字段

MongoDB中的不同查詢運算符對null值的處理也不同。

準備數據:

import pymongoclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test6# 插入兩個文檔,一個item為空值,一個item字段缺失 db.inventory.insert_many([{"_id": 1, "item": None}, {"_id": 2}])

相等性過濾

{'item': None}查詢將匹配要么item字段為空值,要么不包含item字段的文檔:

cursor = db.inventory.find({'item': None} )""" [{u 'item': None,u '_id': 1 }, {u '_id': 2 }] """

類型檢查

{'item': {'$type': 10}}查詢只匹配item為空值的文檔。空值的類型碼是10

cursor = db.inventory.find({'item': {'$type': 10}} )""" [{u'item': None, u'_id': 1}] """

存在檢查

{'item': {'$exists': False}}查詢只匹配不包含item字段的文檔

cursor = db.inventory.find({'item': {'$exists': False}} )""" [{u'_id': 2}] """

更新文檔

更新文檔主要使用如下幾個方法:

  • db.collection.update_one() 最多更新一個文檔(即使匹配出多個)
  • db.collection.update_many() 更新所有匹配的文檔
  • db.collection.replace_one()最多替換一個文檔(即使匹配出過個)
  • db.collection.update()
    • 如果匹配處單個文檔,則進行更新或替換
    • 如果匹配出多個文檔,則更新這些文檔

準備數據:

db.inventory.insert_many([{"item": "canvas","qty": 100,"size": {"h": 28, "w": 35.5, "uom": "cm"},"status": "A"},{"item": "journal","qty": 25,"size": {"h": 14, "w": 21, "uom": "cm"},"status": "A"},{"item": "mat","qty": 85,"size": {"h": 27.9, "w": 35.5, "uom": "cm"},"status": "A"},{"item": "mousepad","qty": 25,"size": {"h": 19, "w": 22.85, "uom": "cm"},"status": "P"},{"item": "notebook","qty": 50,"size": {"h": 8.5, "w": 11, "uom": "in"},"status": "P"},{"item": "paper","qty": 100,"size": {"h": 8.5, "w": 11, "uom": "in"},"status": "D"},{"item": "planner","qty": 75,"size": {"h": 22.85, "w": 30, "uom": "cm"},"status": "D"},{"item": "postcard","qty": 45,"size": {"h": 10, "w": 15.25, "uom": "cm"},"status": "A"},{"item": "sketchbook","qty": 80,"size": {"h": 14, "w": 21, "uom": "cm"},"status": "A"},{"item": "sketch pad","qty": 95,"size": {"h": 22.85, "w": 30.5, "uom": "cm"},"status": "A"}])

更新集合中的文檔

如果要修改字段的值,可以使用更新運算符,比如$set,基本格式如下:

{<更新運算符>: {<字段1>: <1>, ...},<更新運算符>: {<字段2>: <2>, ...}, }

更新單個文檔:update_one()

res = db.inventory.update_one({'item': 'paper'}, # filter{ # update'$set': {'size.uom': 'cm','status': 'P'},'$currentDate': {'lastModified': True # 新增lastModified字段,值是當前時間}} )print(res) # <pymongo.results.UpdateResult object at 0x0000024A22FFB3C8> print(res.matched_count) # 1 print(res.modified_count) # 1cursor = db.inventory.find({'item': 'paper'}) docs = [doc for doc in cursor] print(docs) """ [{'_id': ObjectId('5c8f8dcfbddaf03aa4b6a409'),'item': 'paper','qty': 100,'size': {'h': 8.5,'w': 11,'uom': 'cm'},'status': 'P','lastModified': datetime.datetime(2019, 3, 18, 12, 36, 45, 391000) }] """

更新多個文檔:update_many()

# 更新qty小于50的文檔 res = db.inventory.update_many({'qty': {'$lt': 50}}, # filter{ # update'$set': {'size.uom': 'in', 'status': 'P'},'$currentDate': {'lastModified': True}} )print(res) # <pymongo.results.UpdateResult object at 0x0000014249CF7488> print(res.matched_count) # 3 print(res.modified_count) # 3cursor = db.inventory.find({'qty': {'$lt': 50}}) docs = [doc for doc in cursor] print(docs) """ [{'_id': ObjectId('5c8f8dcfbddaf03aa4b6a405'),'item': 'journal','qty': 25,'size': {'h': 14,'w': 21,'uom': 'in'},'status': 'P','lastModified': datetime.datetime(2019, 3, 19, 12, 26, 33, 410000) }, {'_id': ObjectId('5c8f8dcfbddaf03aa4b6a407'),'item': 'mousepad','qty': 25,'size': {'h': 19,'w': 22.85,'uom': 'in'},'status': 'P','lastModified': datetime.datetime(2019, 3, 19, 12, 26, 33, 413000) }, {'_id': ObjectId('5c8f8dcfbddaf03aa4b6a40b'),'item': 'postcard','qty': 45,'size': {'h': 10,'w': 15.25,'uom': 'in'},'status': 'P','lastModified': datetime.datetime(2019, 3, 19, 12, 26, 33, 414000) }] """

替換文檔:replace_one()

如果要替換整個文檔的內容(除了_id字段),只需傳入一個新的文檔,作為replace_one()的第二個參數即可。替換的文檔只能包含鍵值對,不能巴博涵其他表達式,比如更新運算符。替換的文檔可以和原文的的字段不同,由于_id不可變,你可以省略_id字段(當然,如果你非要在替換文檔中包含_id字段,那么必須給出與原文檔一樣的值)

# 替換滿足篩選條件的第一個文檔 res = db.inventory.replace_one({'item': 'paper'}, # filter{'item': 'paper', # replacement_doc'instock': [{"warehouse": "A", "qty": 60},{"warehouse": "B", "qty": 40}]} )print(res) # <pymongo.results.UpdateResult object at 0x000001AD62170448> print(res.matched_count) # 1 print(res.modified_count) # 1cursor = db.inventory.find({'item': 'paper'}) docs = [doc for doc in cursor] print(docs) """ [{'_id': ObjectId('5c8f8dcfbddaf03aa4b6a409'),'item': 'paper','instock': [{'warehouse': 'A','qty': 60}, {'warehouse': 'B','qty': 40}] }] """

更新行為

原子性

MongoDB的所有寫操作在單個文檔上都是原子性的。

_id字段

一旦設置,該字段的值不可修改,也不能被替換。

字段順序

MongoDB保持寫操作中文檔的順序,除了以下情況:

  • _id字段總是文檔中的第一個字段
  • 如果更新包含對字段進行命名的操作,可能導致文檔的字段重新排序

upsert選項

調用update_one(), update_many(), replace_one()這些方法時,如果指定upsert=True,那么當匹配的文檔不存在時,將創建新的文檔并插入。

刪除文檔

刪除文檔的方法:

  • db.collection.deleteOne() 最多刪除一個文檔(即便匹配出多個結果)
  • db.collection.deleteMany() 刪除匹配的所有文檔
  • db.collection.remove() 刪除匹配的單個或多個文檔

準備數據:

import pymongoclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test8db.inventory.insert_many([{"item": "journal","qty": 25,"size": {"h": 14, "w": 21, "uom": "cm"},"status": "A"},{"item": "notebook","qty": 50,"size": {"h": 8.5, "w": 11, "uom": "in"},"status": "P"},{"item": "paper","qty": 100,"size": {"h": 8.5, "w": 11, "uom": "in"},"status": "D"},{"item": "planner","qty": 75,"size": {"h": 22.85, "w": 30, "uom": "cm"},"status": "D"},{"item": "postcard","qty": 45,"size": {"h": 10, "w": 15.25, "uom": "cm"},"status": "A"}])

刪除所有文檔

如果要刪除所有文檔,只需給delete_many()方法的filter傳入一個空文檔即可

res = db.inventory.count_documents({}) # 查看所有文檔數 print(res) # 5 res = db.inventory.delete_many({}) print(res.deleted_count) # 5

刪除滿足條件的所有文檔

只需給delete_many()方法的filter傳入過濾條件即可,比如

# 刪除status是A點所有文檔 res = db.inventory.delete_many({'status': 'A'}) print(res.deleted_count) # 2

只刪除滿足條件的一個文檔

count = db.inventory.count_documents({'status': 'D'}) cursor = db.inventory.find({'status': 'D'}) print(count) # 2 print([item for item in cursor]) """ [{'_id': ObjectId('5c922bb5bddaf04be0e84076'),'item': 'paper','qty': 100,'size': {'h': 8.5,'w': 11,'uom': 'in'},'status': 'D' }, {'_id': ObjectId('5c922bb5bddaf04be0e84077'),'item': 'planner','qty': 75,'size': {'h': 22.85,'w': 30,'uom': 'cm'},'status': 'D' }] """db.inventory.delete_one({'status': 'D'}) count = db.inventory.count_documents({'status': 'D'}) cursor = db.inventory.find({'status': 'D'}) print(count) print([item for item in cursor]) # 滿足條件的第一個文檔已被刪除 """ [{'_id': ObjectId('5c922bb5bddaf04be0e84077'),'item': 'planner','qty': 75,'size': {'h': 22.85,'w': 30,'uom': 'cm'},'status': 'D' }] """

刪除行為

索引

刪除操作不會刪除索引,即使從表中刪除所有文檔。

原子性

單個文檔的級別上是原子性操作。

批量寫操作:

批量寫操作只對單個集合有效。insert_many()能進行批量插入,另外,bulk_write()方法支持如下的多種寫操作:

  • insert_one
  • update_one
  • update_many
  • replace_one
  • delete_one
  • delete_many

將每種操作放在列表中,然后傳給bulk_write()

下面我們來試一下,準備數據:

import pymongoclient = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test8res = db.characters.insert_many([{"_id": 1, "char": "Brisbane", "class": "monk", "lvl": 4},{"_id": 2, "char": "Eldon", "class": "alchemist", "lvl": 3},{"_id": 3, "char": "Meldane", "class": "ranger", "lvl": 3} ])print(res.inserted_ids) # [1, 2, 3]

使用bulk_write()對characters集合執行多個操作:

import pymongo from pymongo import InsertOne, UpdateOne, DeleteOne, ReplaceOne # 導入各操作對象client = pymongo.MongoClient('mongodb://localhost:27017/') db = client.test8try:res = db.characters.bulk_write([InsertOne({'_id': 4, 'char': 'Dithras', 'class': 'barbarian', 'lvl': 4}),InsertOne({'_id': 5, 'char': 'Taeln', 'class': 'fighter', 'lvl': 3}),UpdateOne({'char': 'Eldon'},{'$set': {'status': 'Critical Injury'}}, upsert=True),UpdateOne({'char': 'Ayhan'},{'$set': {'status': 'God hit'}}, upsert=True),ReplaceOne({'char': 'Meldane'},{"char": "Tanys", "class": "oracle", "lvl": 4}, upsert=True),DeleteOne({'char': 'Brisbane'}),])print(res.inserted_count) # 2print(res.modified_count) # 2print(res.upserted_count) # 1print(res.deleted_count) # 1# 以上打印方式比較繁瑣,也可以這樣直接打印本次批量操作的詳細信息:print(res.bulk_api_result) except Exception as e:print(e)cursor = db.characters.find({}) print([item for item in cursor]) """ [{'_id': 2,'char': 'Eldon','class': 'alchemist','lvl': 3,'status': 'Critical Injury' }, {'_id': 3,'char': 'Tanys','class': 'oracle','lvl': 4 }, {'_id': 4,'char': 'Dithras','class': 'barbarian','lvl': 4 }, {'_id': 5,'char': 'Taeln','class': 'fighter','lvl': 3 }, {'_id': ObjectId('5c92fc403744b8cc2b23f3c3'),'char': 'Ayhan','status': 'God hit' }] """

分片集合的批量插入策略

暫不討論。

索引

添加索引可以加速特定的查詢,也可以為文檔在查詢和存儲增加額外的功能。下面演示下如何用PyMongo創建unique索引:

db.user.create_index([('user_id', pymongo.ASCENDING) ], unique=True)print(list(db.user.index_information())) """ ['_id_', 'user_id_1']_id_ 是MongoDB自動創建的索引 user_id_1 是我們剛剛創建的索引 """

創建了唯一索引約束后,如果插入數據的user_id字段的值在集合中已經存在,會插入失敗。

聚合

準備數據:

import pymongoclient = pymongo.MongoClient(host='localhost', port=27017) db = client.test9db.things.insert_many([{'x': 1, 'tags': ['dog', 'cat']},{'x': 2, 'tags': ['cat']},{'x': 2, 'tags': ['mouse', 'cat', 'dog']},{'x': 3, 'tags': []}, ])

Pipeline聚合

下面執行一個簡答的聚合操作,統計集合內tags數組內每個元素的出現次數。要實現這個操作,需要傳入3個操作給pipeline,首先展開tags數組,然后按元素進行分組并加總,最后根據加總數進行排序即可。

注意,由于python的字典是無序的,如果要求精確排序(比如$sort),就得使用SON或者collections.OrderedDict對象:

import pymongo from bson.son import SON import pprintclient = pymongo.MongoClient(host='localhost', port=27017) db = client.test9pipeline = [{'$unwind': '$tags'},{'$group': {'_id': '$tags', 'count': {'$sum': 1}}}, # 以元素作為_id字段的值,以元素個數作為count字段的值,1表示正加總(-1則進行負加總){'$sort': SON([('count', -1), ('_id', -1)])} # 先按count, 再按_id排序,-1表示倒序 ] pprint.pprint(list(db.things.aggregate(pipeline))) """ [{'_id': 'cat', 'count': 3},{'_id': 'dog', 'count': 2},{'_id': 'mouse', 'count': 1}] """# 如果顛倒排序順序為: {'$sort': SON([('_id', -1), ('count', -1)])},結果如下: """ [{'_id': 'mouse', 'count': 1},{'_id': 'dog', 'count': 2},{'_id': 'cat', 'count': 3}] """# 如果想查看該操作的詳細信息,可以使用command()方法: res = db.command('aggregate', 'things', pipeline=pipeline, explain=True) pprint.pprint(res) """ {'ok': 1.0,'stages': [{'$cursor': {'fields': {'_id': 0, 'tags': 1},'query': {},'queryPlanner': {'indexFilterSet': False,'namespace': 'test9.things','parsedQuery': {},'plannerVersion': 1,'rejectedPlans': [],'winningPlan': {'direction': 'forward','stage': 'COLLSCAN'}}}},{'$unwind': {'path': '$tags'}},{'$group': {'_id': '$tags', 'count': {'$sum': {'$const': 1}}}},{'$sort': {'sortKey': {'_id': -1, 'count': -1}}}]} """

聚合框架還可以提供投影能力來重塑返回的數據。利用投影和聚合,你可以在結果中增加計算字段,創建虛擬子對象,或者提取子字段為根級字段。更多查看:聚合框架

Map / Reduce 聚合

另一種實現聚合的方式是使用map reduce,下面我們通過定義map和reduce函數來實現上面的聚合計算。

map函數循環數組,對其中的每個元素觸發一個鍵值對兒(key, 1):

高級 Map / Reduce

寫入重試

寫操作時,如果發生網絡錯誤,是否支持重試。在pymongo中,可以在實例化客戶端時指定,比如:

client = pymongo.MongoClient(host='localhost',port=27017,retryWrites=True # 默認是False,具體可以查看源碼中的doc )

文本搜索

MongoDB支持通過$text運算符對文本字段作索引,以方便文本搜索。不過嘛,不支持中文,洗洗睡。。。

運算符列表:

名稱描述
$or邏輯或
$eq等于
$gt大于
$gte大于等于
$in在數組中
$lt小于
$lte小于等于
$ne不等于
$nin不在數組中
$elemMatch數組元素滿足
$all數組包含元素
$slice數組切片
$type字段值類型檢查
$exists字段是否存在判斷
$set更新字段的值
$currentDate設定某字段的值為當前日期時間
$inc增加某字段的值
$push為數組字段添加新的元素

mongoengine

待完善。

總結

以上是生活随笔為你收集整理的mongo数据库CRUD的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

avwww在线观看| 亚洲电影自拍 | 亚洲精品国产精品乱码不99热 | 亚洲国产欧美在线看片xxoo | 国产精品av免费观看 | 人人看人人爱 | 99热在线看 | 97精品国产97久久久久久久久久久久 | 国产人成看黄久久久久久久久 | 国产亚洲一区 | 国产 视频 高清 免费 | 久久精品伊人 | 色综合色综合久久综合频道88 | 91免费的视频在线播放 | 免费日韩视 | 日韩欧美一区二区不卡 | 国产精品视频永久免费播放 | 天天做日日爱夜夜爽 | 久久精品国产免费看久久精品 | 成年人视频免费在线播放 | 日韩最新理论电影 | www.久久爱.cn | 国产高清不卡 | 久久免费av电影 | 国产91全国探花系列在线播放 | 久久a视频 | 黄av免费在线观看 | 高潮久久久久久 | 男女激情免费网站 | 又黄又色又爽 | 久久久精品| 国产老妇av | 激情网色 | 91亚洲国产成人 | 九九热av | 婷婷六月天综合 | 久久伊人色综合 | 日韩av专区 | 久久精品99精品国产香蕉 | 久久成人欧美 | 久久爽久久爽久久av东京爽 | 亚洲精品视频在线观看免费视频 | 91成人精品观看 | 久久午夜免费观看 | 成人精品影视 | 国产精品18久久久久久不卡孕妇 | 91插插视频 | 97香蕉久久超级碰碰高清版 | 在线草 | 国产精品毛片一区视频播 | 人人澡人人澡人人 | 久久精品视频网 | 精品特级毛片 | 国产亚洲日| a'aaa级片在线观看 | 精精国产xxxx视频在线播放 | 成人91视频| 一区二区三区四区久久 | 免费 在线 中文 日本 | 69亚洲精品 | 999在线视频 | 伊人黄色网 | 91女神的呻吟细腰翘臀美女 | 免费又黄又爽视频 | 国产中文字幕视频在线观看 | 四虎影视成人永久免费观看亚洲欧美 | 国产精品电影一区二区 | 亚洲一区日韩精品 | 久操伊人 | 国产探花视频在线播放 | 欧美一级艳片视频免费观看 | 日本久久电影网 | 久久97久久97精品免视看 | 久久成人免费电影 | 麻豆传媒一区二区 | 欧美视频99 | 日本论理电影 | 亚洲精品xxxx | 在线视频欧美亚洲 | 成人 亚洲 欧美 | 国产99久久99热这里精品5 | 日本黄色免费大片 | 欧美日韩综合在线 | 国产福利一区二区三区视频 | av电影免费 | 狠狠躁夜夜躁人人爽超碰97香蕉 | 国产 日韩 在线 亚洲 字幕 中文 | 国产精品女教师 | 国产裸体bbb视频 | 丁香伊人网 | av成人免费在线看 | 久草精品网 | 91视频在线观看大全 | 中文字幕黄网 | 999成人免费视频 | 天天操天天射天天添 | 欧美a免费 | 五月天开心 | 日韩91精品 | 韩国精品福利一区二区三区 | 麻豆va一区二区三区久久浪 | 中文字幕在线观看一区二区三区 | 色99久久 | 97碰碰精品嫩模在线播放 | 国际精品久久久 | 亚洲一区精品二人人爽久久 | 午夜久久影视 | 美女视频永久黄网站免费观看国产 | 69久久久久久久 | 日日摸日日 | 日韩在线观看小视频 | 91精品一区二区在线观看 | 日韩爱爱网站 | 久久美女高清视频 | 人人爽人人爽 | 91在线日本| 亚洲精品中文在线 | 全黄网站 | 一本之道乱码区 | 国产小视频在线 | 国产精品自产拍 | 亚洲日本色 | 成人免费大片黄在线播放 | 国内精品久久久久久久久久久 | 天天射天天爱天天干 | 成年人黄色免费网站 | 午夜三级影院 | 日本中文字幕在线观看 | 视频在线亚洲 | 国产婷婷一区二区 | 久久夜av | 99色网站 | 超级碰碰免费视频 | 黄色av电影一级片 | 国产小视频在线免费观看 | 国产四虎影院 | 麻豆国产电影 | 国产麻豆传媒 | a午夜电影| 男女男视频 | 国产伦理久久精品久久久久_ | 网站在线观看日韩 | 一级淫片在线观看 | 91精品国产网站 | 麻豆影音先锋 | 波多野结衣久久资源 | 久久观看 | 日韩在线第一区 | 国产专区视频在线 | 波多野结衣网址 | 亚洲一区视频在线播放 | 色综合中文综合网 | 精品久久精品久久 | 色综合天天狠天天透天天伊人 | 久草精品视频在线看网站免费 | 黄色免费视频在线观看 | 久久久久久毛片精品免费不卡 | 日韩成人看片 | 国产精品成 | 99在线精品视频在线观看 | 正在播放一区 | 天天插日日操 | 肉色欧美久久久久久久免费看 | 波多野结衣在线观看一区二区三区 | 日韩精品一区二区三区外面 | 日韩三级视频在线看 | 国产一区二区影院 | 久久久91精品国产一区二区精品 | 国产视频 亚洲精品 | 色婷婷激情综合 | 啪嗒啪嗒免费观看完整版 | 国产色拍拍拍拍在线精品 | 国产 精品 资源 | 精品中文字幕在线观看 | 99久视频| 欧美成亚洲 | 久久免费播放 | 免费99| 在线观看免费一级片 | 亚洲波多野结衣 | 欧美二区视频 | 亚洲日本三级 | 999男人的天堂 | 欧美小视频在线 | 日韩精品一卡 | 91女神的呻吟细腰翘臀美女 | 在线你懂的视频 | 久久视频在线观看 | 最近中文字幕免费av | 怡红院成人在线 | 国产精品18久久久久久不卡孕妇 | 日韩99热 | 国产成人精品一区二区三区 | 中文亚洲欧美日韩 | 亚洲人视频在线 | 欧美一级电影片 | 91禁看片| 在线观看视频你懂得 | 欧美一级片免费在线观看 | 中文字幕日本电影 | www黄免费 | 欧美激情视频三区 | 日韩色中色 | 国产视频一区在线免费观看 | 亚洲伦理精品 | 免费在线激情电影 | 人人爽夜夜爽 | 欧美日韩三级在线观看 | 天天干天天玩天天操 | 国产中文在线字幕 | 色噜噜日韩精品一区二区三区视频 | 久久国产精品99久久久久久丝袜 | 永久免费的av电影 | 最新av在线播放 | 高清不卡一区二区三区 | 美女视频黄频大全免费 | 国产精品久久久一区二区三区网站 | 色小说av | 99久久精品国产亚洲 | 欧美在线aa| 天天综合久久综合 | 在线观看欧美成人 | 精品一区二区三区四区在线 | 日日操日日操 | 久久狠狠干 | 在线日本看片免费人成视久网 | 午夜av在线播放 | 日韩在线观看一区二区三区 | 这里只有精彩视频 | 亚洲激情网站免费观看 | 最近免费中文视频 | 午夜在线资源 | 久久精品久久精品久久39 | 国产999精品| 久久精品亚洲精品国产欧美 | 狠狠色噜噜狠狠狠狠2021天天 | 日黄网站| 91麻豆精品国产91 | 视色网站 | 天天视频色版 | 久久99精品久久只有精品 | 婷婷视频在线 | 国产精品久久久久aaaa | 亚洲无人区小视频 | 国产精品视频免费看 | 午夜国产福利视频 | 国产亚洲va综合人人澡精品 | 成人午夜电影在线播放 | 亚洲成熟女人毛片在线 | 欧美精品在线免费 | 日韩成人免费在线观看 | 日韩av成人在线 | 97超级碰碰碰碰久久久久 | 九九色综合 | 波多野结衣精品视频 | 国产日韩视频在线播放 | 午夜精品三区 | 久久国产精品久久精品 | aaa亚洲精品一二三区 | 亚洲精品视频在线播放 | 97国产情侣爱久久免费观看 | 在线日韩视频 | 91视频成人免费 | 国产精品久久久久久一区二区三区 | 亚洲国产美女久久久久 | 综合网久久 | 中文字幕一区av | 一区二区三区中文字幕在线 | 天天天插 | 国产xxxx| 日韩免费视频线观看 | 激情丁香综合五月 | 色综合欧洲| 99热在线观看 | 蜜臀久久99精品久久久无需会员 | 国产视频精品久久 | 四虎在线免费观看视频 | 久久精品之 | 蜜臀久久99精品久久久久久网站 | 婷婷色资源 | 婷婷色在线 | 91视频免费 | 在线视频免费观看 | 99精品视频网 | www操操操| www.伊人网| 亚洲福利精品 | 91亚洲精品久久久蜜桃 | 国产高清视频色在线www | 久久综合九色综合网站 | 成人永久免费 | 免费看的国产视频网站 | 中文字幕在线观看播放 | 成人av电影免费 | 国产精品精品视频 | 精品一区二区影视 | 日韩高清激情 | 中文字幕中文 | 中文字幕一区av | 99这里只有精品视频 | 国产一级视频在线免费观看 | 欧美一区二区三区激情视频 | 欧美日韩亚洲第一 | 久久不卡日韩美女 | 亚洲一区二区三区毛片 | 激情丁香久久 | 久久精品一区二 | 久久99亚洲精品久久久久 | 欧美xxxxx在线视频 | 在线免费看片 | 五月婷婷爱 | 日韩精品视频在线观看免费 | 午夜视频在线观看欧美 | 在线视频 91 | 国产精品久久久久久久久久东京 | 米奇四色影视 | 婷婷在线看 | 91超级碰碰| 天天干夜夜 | 亚洲精品免费视频 | 91香蕉视频在线下载 | 免费在线观看不卡av | 成人禁用看黄a在线 | 成人影音在线 | 亚洲精品久 | 日韩日韩日韩日韩 | 国产免费激情久久 | 欧美日韩视频在线一区 | 国产一区二区免费在线观看 | 国产精品视频地址 | 日韩欧美高清视频在线观看 | 欧美日韩伦理在线 | 午夜国产在线观看 | 中国老女人日b | 国产精品久久久久久久久久妇女 | 超碰在线人人97 | 美女网站视频色 | 亚洲v欧美v国产v在线观看 | 99久久激情视频 | 黄色在线看网站 | 天天鲁一鲁摸一摸爽一爽 | 综合在线亚洲 | 99精品国产免费久久 | 99精品久久久久久久 | 五月天中文在线 | 国产亚洲情侣一区二区无 | 国产乱老熟视频网88av | 中文字幕中文中文字幕 | 狠狠亚洲| 日韩精品在线看 | 久久久精品综合 | 99久久99久久精品免费 | 免费福利片2019潦草影视午夜 | 在线视频欧美精品 | 久草网在线视频 | 一区二区三区四区精品视频 | 99精品一级欧美片免费播放 | 最近中文字幕国语免费av | 国产电影一区二区三区四区 | 91精品国产乱码久久 | 久9在线| 日日日日日 | 99久久激情 | 91成人精品一区在线播放69 | 久久99热这里只有精品国产 | 91tv国产成人福利 | 久久久夜色 | 国内精品在线一区 | 婷婷婷国产在线视频 | 精品久久久久久久久久久久久久久久 | 久久综合九色综合欧美狠狠 | 综合色久 | 国产999免费视频 | av网站免费线看精品 | 精品国产一区二 | 久热香蕉视频 | 九九久久精品视频 | 97爱| 超碰在线97观看 | 亚洲电影黄色 | 亚洲激情视频在线 | 美女黄视频免费看 | 免费观看黄 | 久久成人麻豆午夜电影 | 热精品 | 久久久久99精品国产片 | 国产成人精品a | 特级毛片网| 久草免费在线观看视频 | 国产视频一区在线免费观看 | 国产精品成人久久久久 | 奇米影视四色8888 | 中文字幕一区二区三区乱码不卡 | 欧美一级片在线播放 | 国产涩涩在线观看 | 亚洲伊人网在线观看 | 精品一区二区综合 | 91成人小视频 | 久久影院一区 | 免费在线观看成人小视频 | 五月激情亚洲 | 91av在线免费视频 | 日韩一区二区三区免费视频 | 久久久 精品 | 天天躁日日躁狠狠躁av中文 | 人人爽人人插 | 丁香视频免费观看 | 黄网站色欧美视频 | 国产精品国产三级国产aⅴ无密码 | 中文字幕在线一二 | 国产午夜精品一区二区三区在线观看 | 中文字幕在线视频免费播放 | 久久久国产电影 | 国产毛片aaa | 91成熟丰满女人少妇 | 中文字幕制服丝袜av久久 | 黄色免费网站 | 亚洲精品色婷婷 | 日韩综合视频在线观看 | 久久久久久久久久久电影 | 岛国精品一区二区 | 亚洲午夜在线视频 | 极品美女被弄高潮视频网站 | 亚洲中字幕 | 99综合电影在线视频 | 中文字幕久久网 | 国产精品久久久久久五月尺 | 精品视频999 | 亚洲天堂网站视频 | 人人干人人超 | 色综合小说| 中文字幕高清在线播放 | 91成人免费看片 | 国产一区福利 | 婷婷六月丁 | 一级片视频在线 | 欧美一区二区三区在线播放 | 国产黄a三级三级三级三级三级 | 欧美日韩中文国产一区发布 | 国产在线精品一区二区三区 | 麻豆免费在线视频 | 欧美片网站yy | 免费欧美精品 | 久久欧美在线电影 | 天堂av色婷婷一区二区三区 | 日韩欧美亚州 | zzijzzij亚洲成熟少妇 | 国产精品初高中精品久久 | 亚洲a成人v | 久久无码av一区二区三区电影网 | 日韩中文字幕免费看 | 国内精品久久久久久 | 在线免费观看视频你懂的 | 在线播放亚洲 | 久久久麻豆视频 | 国产一级二级三级在线观看 | 日韩欧美在线影院 | 青青网视频 | 亚洲国产一区av | 最新色站| 精品国产一区二区三区男人吃奶 | 免费三级黄 | 久久午夜精品 | 999久久久精品视频 日韩高清www | 97国产大学生情侣酒店的特点 | 一区在线电影 | 午夜电影 电影 | 欧美精品生活片 | 在线精品视频在线观看高清 | 日韩黄色在线观看 | www天天干| 欧美精品久久久久性色 | 六月色丁 | av不卡免费在线观看 | 高清精品久久 | 免费在线看成人av | 午夜精品一区二区三区四区 | 国产精品成人自产拍在线观看 | 亚洲 欧美 成人 | 亚洲精品国产精品乱码在线观看 | 久久草草热国产精品直播 | 亚洲欧美视频在线观看 | 久久久这里有精品 | 日韩精品一区在线播放 | 日韩国产欧美在线视频 | www.久久爱.cn| 婷婷亚洲五月色综合 | 999久久久免费视频 午夜国产在线观看 | 国产免码va在线观看免费 | 婷婷精品国产欧美精品亚洲人人爽 | 激情网综合 | 在线观看911视频 | 99视频精品在线 | 欧美一区二区三区在线播放 | 四虎国产精品永久在线国在线 | 夜夜爽www| 综合激情网 | 国产99久久久国产精品成人免费 | 99久久网站 | 亚洲视频999 | 久久香蕉国产精品麻豆粉嫩av | 欧美福利精品 | 日日精品 | 狠狠操.com| 黄色av电影 | 亚洲精品av在线 | 欧美日韩免费一区二区三区 | 中文字幕网址 | 精品国自产在线观看 | 成人a v视频 | 五月精品| 日韩高清www| 国产精品激情 | 成人免费观看在线视频 | 婷婷在线网 | 亚洲天天在线日亚洲洲精 | 在线观看91久久久久久 | 夜夜操天天 | 免费成人在线视频网站 | 伊人亚洲综合网 | 免费av福利 | 精品国产亚洲一区二区麻豆 | 午夜精品久久久 | 探花视频在线观看 | 免费看的黄色录像 | 97视频亚洲 | 亚洲成aⅴ人片久久青草影院 | 成人三级av | 中文字幕免费 | 国产色拍拍拍拍在线精品 | 成全免费观看视频 | 国产最新在线观看 | 91成人久久 | 69久久夜色精品国产69 | 天天综合网~永久入口 | 在线免费中文字幕 | 99久久精品国产一区二区三区 | 五月天六月婷 | 色久综合 | 国产永久免费高清在线观看视频 | 久久久精品日本 | 国内精品久久久久久久久久清纯 | 日日摸日日爽 | 亚洲精品综合久久 | 色爱成人网 | 欧美一级xxxx | 久热电影 | 在线你懂 | 国产免费二区 | 永久中文字幕 | 日韩一区二区免费在线观看 | 亚洲午夜精品电影 | 精品免费久久久久久 | 婷婷色影院 | 国产成人精品免费在线观看 | 夜夜躁天天躁很躁波 | 久久激情五月丁香伊人 | 97精品在线| 国产黄免费在线观看 | 丝袜护士aⅴ在线白丝护士 天天综合精品 | 色综合天天在线 | 欧美日韩在线视频免费 | 国产午夜三级一二三区 | 91精品婷婷国产综合久久蝌蚪 | 国产精品久久久久毛片大屁完整版 | 婷婷在线免费观看 | 香蕉视频在线视频 | 97狠狠操 | 国产xxxxx在线观看 | 国产精品视频免费看 | 91中文字幕在线视频 | 九九涩涩av台湾日本热热 | 免费影视大全推荐 | 国产精品一区二区三区在线播放 | 在线免费国产视频 | 在线亚洲人成电影网站色www | 91亚洲精品在线观看 | 精品国产欧美一区二区三区不卡 | 天天干天天做天天爱 | 久久久毛片 | 欧美极度另类性三渗透 | 青青河边草免费观看 | 久久久www | 色综合久久久久久久 | 久久夜av | 久久 亚洲视频 | 久久久久久久网 | 黄色大片国产 | a黄色一级| 亚洲国产av精品毛片鲁大师 | 欧美日韩国产mv | 在线视频91 | 国产在线视频资源 | 国产一级片免费视频 | 六月婷婷色 | a视频在线| 亚洲免费在线播放视频 | 精品在线视频播放 | 香蕉网站在线观看 | 韩国精品福利一区二区三区 | 九九在线视频 | 免费高清在线视频一区· | 丁香婷婷激情 | 天天操天操 | 国产男女无遮挡猛进猛出在线观看 | 久久综合九色99 | 国产一区在线视频观看 | 国产精品久久久久久吹潮天美传媒 | 中国美女一级看片 | 欧美日韩一区二区在线观看 | 色99之美女主播在线视频 | 欧美一级免费高清 | 日韩在线观看高清 | 日韩av在线网站 | 日韩激情视频在线观看 | 欧美性生活久久 | 福利视频区 | 日韩色综合网 | 久久精品99国产精品亚洲最刺激 | 免费一级片在线观看 | www国产在线 | 在线精品国产 | 久久96国产精品久久99软件 | 国产一区影院 | 国产精品一区二区吃奶在线观看 | 香蕉视频导航 | 国产福利精品一区二区 | 精品日韩在线 | 成年人视频在线免费播放 | 国产日韩一区在线 | 99久久久国产精品免费观看 | 欧美一区在线观看视频 | 精品免费视频. | 国产精品专区h在线观看 | 激情中文在线 | 免费观看性生活大片3 | 日韩av免费一区二区 | 激情五月婷婷激情 | 在线国产一区二区 | 国产高清小视频 | 日韩毛片久久久 | 超碰97在线资源站 | 欧美成人h版电影 | 在线免费色视频 | 又污又黄的网站 | 西西人体4444www高清视频 | 亚洲欧美综合精品久久成人 | 免费一级毛毛片 | 五月天婷亚洲天综合网鲁鲁鲁 | 久久婷婷精品 | 日韩在线视频看看 | 在线观看国产 | 日韩精品专区在线影院重磅 | 亚洲激情精品 | 中文区中文字幕免费看 | 天堂av在线 | 中文字幕第一页在线播放 | 黄色小说18 | 91亚洲欧美 | 亚洲成av人片在线观看 | 久久久久久久久久久久久9999 | 国内久久| 亚洲免费激情 | 久久久久久久久久久久久久电影 | 久久亚洲成人网 | a爱爱视频 | 欧美吞精 | 日本午夜在线亚洲.国产 | 99精品久久久久久久久久综合 | 麻豆免费视频网站 | 免费在线观看91 | 欧美日韩高清一区 | 深爱五月网| 99久久99| 国产精品一区二区吃奶在线观看 | 国产成人综合精品 | 91久久爱热色涩涩 | 日韩特黄一级欧美毛片特黄 | 最近中文字幕久久 | www.色com| 五月天激情综合网 | 精壮的侍卫呻吟h | 国外av在线 | 欧美午夜性生活 | 日韩成人欧美 | 国产色啪| 在线观看中文字幕一区 | 中文在线字幕免费观看 | 91视频在线网址 | 97精品久久人人爽人人爽 | 在线天堂中文www视软件 | 日韩欧美视频在线 | 免费三级黄 | 成年人在线免费看片 | 波多野结衣网址 | 免费精品视频在线观看 | 国产一区二区免费在线观看 | 99久久精品免费看国产麻豆 | 激情偷乱人伦小说视频在线观看 | 日韩有码在线观看视频 | 五月天激情电影 | 婷婷 中文字幕 | 日韩欧美视频免费在线观看 | av大全在线播放 | 日韩中文字幕国产精品 | 国外调教视频网站 | 成人cosplay福利网站 | 国产一区二区三区免费在线 | av中文字幕不卡 | 在线黄网站 | 免费午夜视频在线观看 | 91精品第一页 | 天堂视频一区 | 久久久久久伊人 | 又污又黄的网站 | zzijzzij日本成熟少妇 | 2021久久| 国产婷婷色| 国产午夜精品一区二区三区嫩草 | 最近免费中文字幕 | 午夜精品久久久久久久久久久久久久 | 天天干中文字幕 | 久久精品com | 人人看看人人 | 不卡精品视频 | 亚洲精品在线免费看 | 久草免费在线视频 | 黄色.com | 久精品视频免费观看2 | 人人射av | 超碰在线97免费 | 91热在线 | 国产在线无| 国产综合在线视频 | 国产成人精品av在线观 | 精品国产一区二区三区噜噜噜 | 天天操天天操天天 | 国产精品久一 | 免费av观看 | 日韩精品 在线视频 | 国产高清在线免费 | 亚洲成人国产精品 | 国产精品一区二区无线 | 精品一区二区日韩 | 中文字幕在线视频一区 | 久久国产精品免费视频 | 亚洲精品乱码久久 | 四虎国产视频 | 中文字幕免费在线 | 97超视频免费观看 | 黄色av电影在线观看 | 国产精品网红福利 | 亚洲欧洲国产日韩精品 | 国产激情小视频在线观看 | 国产亚洲成人网 | 探花视频在线观看+在线播放 | 久久天天躁夜夜躁狠狠躁2022 | 国产精品毛片一区视频播不卡 | 国产 日韩 在线 亚洲 字幕 中文 | 五月亚洲 | 91精品999| 国产中文在线字幕 | 精品99久久 | 国产伦精品一区二区三区无广告 | 免费日韩 精品中文字幕视频在线 | 亚洲成av | 97碰碰精品嫩模在线播放 | 成人一区二区在线观看 | 久久伦理 | 91福利视频久久久久 | 超碰国产在线观看 | 狠狠色噜噜狠狠狠合久 | 一本一本久久aa综合精品 | 日韩剧情 | 婷婷爱五月天 | 美女网站久久 | 天天综合婷婷 | 亚洲一二区视频 | 九九久久久久久久久激情 | 香蕉网在线 | 黄色的网站在线 | 最新色视频 | 午夜精品一区二区三区在线播放 | 亚洲va综合va国产va中文 | 亚洲精品一区二区网址 | 毛片激情永久免费 | 免费在线观看日韩视频 | 欧美日韩二三区 | 亚洲久草网 | 久久久久久久久影院 | 9久久精品 | 日韩中文字幕亚洲一区二区va在线 | 五月婷婷久草 | 婷婷在线视频观看 | 天天射天天射天天射 | 看毛片网站 | 久久精彩视频 | 91精品91 | 99 精品 在线| 色噜噜日韩精品一区二区三区视频 | 九九九九精品九九九九 | 4hu视频| 激情视频一区 | 国产精品嫩草影视久久久 | 99精品国产99久久久久久福利 | 亚洲黄色精品 | 黄色av三级在线 | 久久视影 | 狠狠黄 | 国内精品视频在线播放 | 免费福利片2019潦草影视午夜 | 国产一区二区三区免费观看视频 | 亚洲欧洲精品一区二区精品久久久 | 99热99| 96精品视频 | 欧美日韩国产一区二区三区在线观看 | 97在线观看免费 | 四虎影视av | 久久在线看 | 婷婷丁香色综合狠狠色 | 久久久久激情 | 一区二区日韩av | 国产剧情在线一区 | 色在线免费观看 | 久草视频免费播放 | 久久不色 | 激情五月婷婷综合 | 天天拍天天操 | 深爱开心激情网 | 成人av片免费看 | 奇米影视四色8888 | 国产你懂的在线 | 国产精品二区在线观看 | 99免费国产 | 一区二区av| 欧美性另类 | 免费日韩一级片 | 久久亚洲私人国产精品va | 久久久国产在线视频 | 国产精品毛片一区视频播不卡 | 久久夜视频 | 蜜臀av性久久久久蜜臀aⅴ四虎 | 日韩成人看片 | 亚洲乱亚洲乱亚洲 | 97久久精品午夜一区二区 | 久久综合激情 | 国产成人免费av电影 | 国内精品久久久久久 | 少妇bbr搡bbb搡bbb | 999国内精品永久免费视频 | 日韩欧美综合精品 | 国产a免费 | 亚洲春色成人 | 久久精品视频网 | 亚洲91av| 久久精品草 | 日韩大陆欧美高清视频区 | 在线视频你懂得 | 久久精品二区 | 四虎成人免费影院 | 久久久免费国产 | 国产精品18久久久久久久久久久久 | 精品欧美小视频在线观看 | 免费在线观看黄色网 | 国产精品理论片在线观看 | 欧美日韩亚洲第一页 | 日本二区三区在线 | 午夜在线免费观看视频 | 中文字幕中文字幕 | 亚洲小视频在线观看 | 久久av中文字幕片 | 精品久久一级片 | 97超碰在线播放 | 欧美福利片在线观看 | av大全在线免费观看 | 91精品久久久久久久久久久久久 | 中国一级片在线观看 | 天堂av网在线 | 欧洲av在线 | 五月婷婷综合在线视频 | 99riav1国产精品视频 | 在线免费观看视频a | 国产va在线 | 97超碰影视 | 一区二区三区在线影院 | 久久久91精品国产一区二区三区 | 中文字幕精品一区二区三区电影 | 国产午夜亚洲精品 | 国产免费三级在线观看 | 天天舔天天搞 | 高清国产一区 | 成人av动漫在线 | 91.精品高清在线观看 | 91成人网在线 | 欧美aa级 | 国产中文字幕在线看 | 97色婷婷| 中文区中文字幕免费看 | 91精品在线免费视频 | 91免费视频网站在线观看 | 午夜av一区 | 欧美精品一区二区免费 | 99视频久久 | 国产97在线观看 | 国产999视频| 国内精品一区二区 | 久久精精品视频 | 在线a视频| 国产一级一片免费播放放a 一区二区三区国产欧美 | 91麻豆国产福利在线观看 | 天天玩天天干天天操 | 在线观看成人毛片 | 欧美日韩视频在线观看一区二区 | 国产成人精品一区二区 | 欧美三级高清 | av色综合网 | 亚洲综合欧美激情 | 国产特级毛片aaaaaa高清 | 在线播放日韩av | 香蕉97视频观看在线观看 | 91av观看 | 一级欧美一级日韩 | 亚洲欧美国产精品久久久久 | 国产夫妻性生活自拍 | 日韩理论在线视频 | 手机色站| 狠狠色狠狠色综合日日92 | 久久久久欧美精品 | 91理论片午午伦夜理片久久 | av色影院| 黄色片软件网站 | 久久欧美在线电影 | 久久亚洲私人国产精品 | 一 级 黄 色 片免费看的 | 亚洲综合视频在线播放 | 免费精品人在线二线三线 | 久草免费在线视频观看 | 在线观看亚洲电影 | 久久久久国产精品视频 | 久青草视频在线观看 | 国产精品国产三级国产aⅴ入口 | 欧美一级片播放 | 久久草av | 免费福利片2019潦草影视午夜 | 免费看一级特黄a大片 | 免费婷婷| 欧美久久久久久久久中文字幕 | 在线天堂日本 | 中文字幕二区在线观看 | 99超碰在线播放 | 91理论电影| 国产精品黄色 | 96亚洲精品久久久蜜桃 | 成人免费在线看片 | 国产资源av | 韩国一区二区三区在线观看 | 欧美va在线观看 | 在线免费色视频 | 激情久久久久久久久久久久久久久久 | 97看片网| 91精品久久久久久粉嫩 | 免费毛片一区二区三区久久久 | 日韩电影在线观看中文字幕 | 综合久久五月天 | 亚洲va在线va天堂va偷拍 | 天天干视频在线 | 日日日操操 | 国产破处精品 | 黄色软件网站在线观看 | 日韩中文字幕国产 | 国产精品99久久久精品免费观看 | 99在线热播精品免费99热 | 久久久午夜精品福利内容 | 欧美一区二区在线 | 国产九九热视频 | 国产99久久精品一区二区300 | 成人午夜网 | 免费看日韩 | 四虎影视成人精品国库在线观看 | 成人性生交大片免费看中文网站 | 午夜少妇av | 久久99精品久久久久久久久久久久 | 色婷婷综合五月 | 亚洲三级影院 | 五月丁色 | 瑞典xxxx性hd极品 | 成年人看片 | 天天色天天干天天色 | 午夜精品久久久久久久99无限制 | 日韩在线第一 | 国产精品毛片久久久久久久 | 在线观看中文字幕dvd播放 | 婷婷丁香综合 | 99精品在线免费观看 | 国内精品久久久久久久久久清纯 | 在线观看视频免费播放 | 久久亚洲欧美日韩精品专区 | 国产福利精品在线观看 |