Python开发之基础Mongodb

Mongodb简介

Mongodb是一个分布式存储的NoSQL数据库,运行稳定、性能高,旨在于为WEB应用提供可扩展的高性能数据存储解决方案。

MongoDB特点:

  • 模式自由:可以把不同结构的文档存储在同一个数据库中。
  • 面向集合的存储:适合存储JSON风格格式的形式
  • 完整的索引支持:对任何属性可索引
  • 复制和高可用性:支持服务器之间的数据复制,支持主从模式以及服务器之间的相互复制。复制的主要目的是提供冗余及自动故障转移。
  • 自动分片:支持云级别的伸缩性,自动分片功能支持水平的数据库集群,可动态添加额外的机器。
  • 丰富的查询:支持丰富的查询表达方式,查询指令使用JSON形式的标记,可轻易的查询文档中的内嵌的对象以及数组
  • 快速就地更新:查询优化器会分析查询表达式,并生成一个高效的查询计划
  • 高效的传统存储方式:支持二进制数据以及大型数据。

Mongodb中的名词

SQL术语 MongoDB术语 说明
database database 数据库
table collection 数据库表/集合
row document 数据记录行/文档
column filed 数据字段/域
index index 索引
table joins   表连接,MongoDB不支持
primary key primary key 主键,MongoDB自动将id设置为主键

MongoDB中的三元素:数据库、集合、文档。

集合就是关系型数据库中的表

文档就是对应关系数据库中的行,文档就是一个对象,由键值对组成,是json的扩展Bson形式

数据库安装 

1、下载完安装包,并解压 tgz

curl -O https://fastdl.mongodb.org/linux/mongodb-linux-x86_64-3.0.6.tgz    # 下载
tar -zxvf mongodb-linux-x86_64-3.0.6.tgz                                   # 解压

mv  mongodb-linux-x86_64-3.0.6/ /usr/local/mongodb    

2、MongoDB 的可执行文件位于 bin 目录下,所以可以将其添加到 PATH 路径中:

export PATH=/usr/local/mongodb/bin:$PATH

3、MongoDB的数据存储在data目录的db目录下,但是这个目录在安装过程不会自动创建,所以你需要手动创建data目录,并在data目录中创建db目录。

mkdir -p /data/db

4、你可以在命令行中执行mongo安装目录中的bin目录执行mongod命令来启动mongdb服务。

./mongod
2018-08-15T22:03:29.771+0800 I STORAGE  [initandlisten] exception in initAndListen: 98 Unable to create/open lock file: /data/db/mongod.lock errno:13 Permission denied Is a mongod instance already running?, terminating
2018-08-15T22:03:29.771+0800 I CONTROL  [initandlisten] dbexit:  rc: 100

如果你在安装目录下执行./mongod报上述错误,表示没有权限,所以就要加权限

sudo chmod 777 -R /data

再次执行./mongod

5、MongoDB后台管理Shell

如果你需要进入MongoDB后台管理,你需要先打开mongodb装目录的下的bin目录,然后执行mongo命令文件。

MongoDB Shell是MongoDB自带的交互式Javascript shell,用来对MongoDB进行操作和管理的交互式环境。

python@python:/usr/local/mongodb/bin$ ./mongo
MongoDB shell version: 3.0.6
connecting to: test
Welcome to the MongoDB shell.
For interactive help, type "help".
For more comprehensive documentation, see
    http://docs.mongodb.org/
Questions? Try the support group
    http://groups.google.com/group/mongodb-user
> 
> 
> 2+3
5

6、MongoDB web用户界面

MongoDB 提供了简单的 HTTP 用户界面。 如果你想启用该功能,需要在启动的时候指定参数 --rest 。

注意:该功能只适用于 MongoDB 3.2 及之前的早期版本。

$ ./mongod --dbpath=/data/db --rest

MongoDB 的 Web 界面访问端口比服务的端口多1000。

如果你的MongoDB运行端口使用默认的27017,你可以在端口号为28017访问web用户界面,即地址为:http://localhost:28017。

数据库基本操作

1、数据库切换

查看当前数据库名称
> db
test
查看所有数据库名称
> show dbs
local  0.078GB
创建数据库
> use test1
switched to db tst

2、数据库删除

数据库删除
db.dropDatabase

3、数据集合

MongoDB 中使用 createCollection() 方法来创建集合。
db.createCollection(name, options)
参数说明:
name: 要创建的集合名称
options: 可选参数, 指定有关内存大小及索引的选项

options 可以是如下参数:

字段 类型 描述
capped 布尔 (可选)如果为 true,则创建固定集合。固定集合是指有着固定大小的集合,当达到最大值时,它会自动覆盖最早的文档。
当该值为 true 时,必须指定 size 参数。
autoIndexId 布尔 (可选)如为 true,自动在 _id 字段创建索引。默认为 false。
size 数值 (可选)为固定集合指定一个最大值(以字节计)。
如果 capped 为 true,也需要指定该字段。
max 数值 (可选)指定固定集合中包含文档的最大数量。

在插入文档时,MongoDB 首先检查固定集合的 size 字段,然后检查 max 字段。

  •  不限制集合的大小
> db.createCollection("name")
{ "ok" : 1 }
  • 创建固定集合 mycol,整个集合空间大小 6142800 KB, 文档最大个数为 10000 个。
> db.createCollection("mycol",{capped:true,autoIndexId:true,size:8142800,max:10000})
{ "ok" : 1 }
  • 如果要查看已有集合,可以使用 show collections 命令:
> show collections
mycol
name
runoob
system.indexes
  • 删除集合:db.集合名称.drop()
> db.mycol.drop()
true

4、数据类型

常见数据类型

  • Object ID:文档类型
  • String:字符串,最常用必须是UTF-8
  • Boolean:存储一个布尔值,true或false
  • Integer:整数可以是32位或64位,取决于服务器
  • Double:存储浮点数
  • Arrays:数组或列表,多个值存储到一个键
  • Object:用于嵌入式的文档,即一个值为一个文档
  • Null:存储Null值
  • Timestamp:时间戳
  • Date:存储当前日期的UNIX时间格式

5、插入

MongoDB 使用 insert() 或 save() 方法向集合中插入文档,语法如下:

db.COLLECTION_NAME.insert(document)
> db.mycol.insert({title:'Mongodb',descr:'课程'})
WriteResult({ "nInserted" : 1 })
> show dbs

6、查找

> db.mycol.find()
{ "_id" : ObjectId("5b7589f65591ee81f5f24102"), "title" : "Mongodb" }
{ "_id" : ObjectId("5b758a145591ee81f5f24103"), "title" : "Mongodb", "descr" : "课程" }

更新

update() 方法用于更新已存在的文档。语法格式如下:

db.collection.update(
   <query>,
   <update>,
   {
     upsert: <boolean>,
     multi: <boolean>,
     writeConcern: <document>
   }
)
参数说明:

query : update的查询条件,类似sql update查询内where后面的。
update : update的对象和一些更新的操作符(如$,$inc...)等,也可以理解为sql update查询内set后面的
upsert : 可选,这个参数的意思是,如果不存在update的记录,是否插入objNew,true为插入,默认是false,不插入。
multi : 可选,mongodb 默认是false,只更新找到的第一条记录,如果这个参数为true,就把按条件查出来多条记录全部更新。
writeConcern :可选,抛出异常的级别。
> db.mycol.find()
{ "_id" : ObjectId("5b7589f65591ee81f5f24102"), "title" : "Mongodb" }
{ "_id" : ObjectId("5b758a145591ee81f5f24103"), "title" : "Mongodb", "descr" : "课程" }
{ "_id" : ObjectId("5b758bc25591ee81f5f24104"), "name" : "hr", "age" : "18" }
> db.mycol.update({name:'hr'},{name:"gj"})
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
> db.mycol.find()
{ "_id" : ObjectId("5b7589f65591ee81f5f24102"), "title" : "Mongodb" }
{ "_id" : ObjectId("5b758a145591ee81f5f24103"), "title" : "Mongodb", "descr" : "课程" }
{ "_id" : ObjectId("5b758bc25591ee81f5f24104"), "name" : "gj" }

以上语句只会修改第一条发现的文档,如果你要修改多条相同的文档,则需要设置 multi 参数为 true

> db.mycol.update({},{$set:{title:'python'}},{multi:true})
WriteResult({ "nMatched" : 3, "nUpserted" : 0, "nModified" : 2 })
> db.mycol.find()
{ "_id" : ObjectId("5b7589f65591ee81f5f24102"), "title" : "python" }
{ "_id" : ObjectId("5b758a145591ee81f5f24103"), "title" : "python", "descr" : "课程" }
{ "_id" : ObjectId("5b758bc25591ee81f5f24104"), "name" : "gj", "title" : "python" }

7、保存

save() 方法通过传入的文档来替换已有文档。语法格式如下:

db.collection.save(
   <document>,
   {
     writeConcern: <document>
   }
)
参数说明:

document : 文档数据。
writeConcern :可选,抛出异常的级别。
> db.mycol.save({name:'java'})
WriteResult({ "nInserted" : 1 })
> db.mycol.find()
{ "_id" : ObjectId("5b7589f65591ee81f5f24102"), "title" : "python" }
{ "_id" : ObjectId("5b758a145591ee81f5f24103"), "title" : "python", "descr" : "课程" }
{ "_id" : ObjectId("5b758bc25591ee81f5f24104"), "name" : "gj", "title" : "python" }
{ "_id" : ObjectId("5b758e725591ee81f5f24105"), "name" : "java" }

8、删除文档

remove() 方法的基本语法格式如下所示:
db.collection.remove(
   <query>,
   <justOne>
)
> db.mycol.find()
{ "_id" : ObjectId("5b7589f65591ee81f5f24102"), "title" : "python" }
{ "_id" : ObjectId("5b758a145591ee81f5f24103"), "title" : "python", "descr" : "课程" }
{ "_id" : ObjectId("5b758bc25591ee81f5f24104"), "name" : "gj", "title" : "python" }
{ "_id" : ObjectId("5b758e725591ee81f5f24105"), "name" : "java" }
> db.mycol.remove({title:'python'})
WriteResult({ "nRemoved" : 3 })
> db.mycol.find()
{ "_id" : ObjectId("5b758e725591ee81f5f24105"), "name" : "java" }

全部删除

> db.mycol.remove({})

9、数据查询

MongoDB 查询数据的语法格式如下:

db.collection.find(query, projection)
query :可选,使用查询操作符指定查询条件
projection :可选,使用投影操作符指定返回的键。查询时返回文档中所有键值, 只需省略该参数即可(默认省略)。
如果你需要以易读的方式来读取数据,可以使用 pretty() 方法,语法格式如下:
>db.col.find().pretty()
> db.mycol.findOne()
{ "_id" : ObjectId("5b7592253a1d5dd1beb2b7ac"), "title" : "js" }
> db.mycol.find().pretty()
{ "_id" : ObjectId("5b7592253a1d5dd1beb2b7ac"), "title" : "js" }
{ "_id" : ObjectId("5b75922d3a1d5dd1beb2b7ad"), "title" : "python" }

10、条件操作符

MongoDB中条件操作符有:

(>) 大于 - $gt
(<) 小于 - $lt
(>=) 大于等于 - $gte
(<= ) 小于等于 - $lte
> db.mycol.insert({age:12})
WriteResult({ "nInserted" : 1 })
> db.mycol.find({'age':{$lt:13}})
{ "_id" : ObjectId("5b7593845591ee81f5f24107"), "age" : 12 }
Select * from mycol where age < 13;

11、模糊匹配

查询 title 包含""字的文档:

db.col.find({title:/教/})
查询 title 字段以""字开头的文档:

db.col.find({title:/^教/})
查询 titl e字段以""字结尾的文档:

db.col.find({title:/教$/})

 12、使用函数查询,其实就是js

> db.mycol.find({$where: function(){return this.age==12}} )
{ "_id" : ObjectId("5b7593385591ee81f5f24106"), "age" : "12" }
{ "_id" : ObjectId("5b7593845591ee81f5f24107"), "age" : 12 }

13、limit

如果你需要在MongoDB中读取指定数量的数据记录,可以使用MongoDB的Limit方法,limit()方法接受一个数字参数,该参数指定从MongoDB中读取的记录条数。

> db.mycol.find().limit(2)
{ "_id" : ObjectId("5b7592253a1d5dd1beb2b7ac"), "title" : "js" }
{ "_id" : ObjectId("5b75922d3a1d5dd1beb2b7ad"), "title" : "python" }

我们除了可以使用limit()方法来读取指定数量的数据外,还可以使用skip()方法来跳过指定数量的数据,skip方法同样接受一个数字参数作为跳过的记录条数。

> db.mycol.find()
{ "_id" : ObjectId("5b7592253a1d5dd1beb2b7ac"), "title" : "js" }
{ "_id" : ObjectId("5b75922d3a1d5dd1beb2b7ad"), "title" : "python" }
{ "_id" : ObjectId("5b7593385591ee81f5f24106"), "age" : "12" }
{ "_id" : ObjectId("5b7593845591ee81f5f24107"), "age" : 12 }
> db.mycol.find().limit(2)
{ "_id" : ObjectId("5b7592253a1d5dd1beb2b7ac"), "title" : "js" }
{ "_id" : ObjectId("5b75922d3a1d5dd1beb2b7ad"), "title" : "python" }
> db.mycol.find().limit(2).skip(1)
{ "_id" : ObjectId("5b75922d3a1d5dd1beb2b7ad"), "title" : "python" }
{ "_id" : ObjectId("5b7593385591ee81f5f24106"), "age" : "12" }
> db.mycol.find().limit(2).skip(2)
{ "_id" : ObjectId("5b7593385591ee81f5f24106"), "age" : "12" }
{ "_id" : ObjectId("5b7593845591ee81f5f24107"), "age" : 12 }

14、排序

在 MongoDB 中使用 sort() 方法对数据进行排序,sort() 方法可以通过参数指定排序的字段,并使用 1 和 -1 来指定排序的方式,其中 1 为升序排列,而 -1 是用于降序排列。

> db.mycol.find().sort({"age":-1})
{ "_id" : ObjectId("5b7593385591ee81f5f24106"), "age" : "12" }
{ "_id" : ObjectId("5b7593845591ee81f5f24107"), "age" : 12 }
{ "_id" : ObjectId("5b75922d3a1d5dd1beb2b7ad"), "title" : "python" }
{ "_id" : ObjectId("5b7592253a1d5dd1beb2b7ac"), "title" : "js" }
> db.mycol.find().sort({"age":-1,"title":1})
{ "_id" : ObjectId("5b7593385591ee81f5f24106"), "age" : "12" }
{ "_id" : ObjectId("5b7593845591ee81f5f24107"), "age" : 12 }
{ "_id" : ObjectId("5b7592253a1d5dd1beb2b7ac"), "title" : "js" }
{ "_id" : ObjectId("5b75922d3a1d5dd1beb2b7ad"), "title" : "python" }

15、统计

> db.sub.find()
{ "_id" : ObjectId("5b7591b73a1d5dd1beb2b7aa"), "title" : "java" }
{ "_id" : ObjectId("5b7591d23a1d5dd1beb2b7ab"), "title" : "python" }
{ "_id" : ObjectId("5b759ade5591ee81f5f24108"), "title" : "c++" }
{ "_id" : ObjectId("5b759ae35591ee81f5f24109"), "title" : "js" }
{ "_id" : ObjectId("5b759ae75591ee81f5f2410a"), "title" : "css" }
> db.sub.find().count()
5

MongoDB聚合操作

聚合

MongoDB中聚合(aggregate)主要用于处理数据(诸如统计平均值,求和等),并返回计算后的数据结果。有点类似sql语句中的 count(*)。

MongoDB中聚合的方法使用aggregate()。

聚合框架中常用的几个操作:

$project:修改输入文档的结构。可以用来重命名、增加或删除域,也可以用于创建计算结果以及嵌套文档。
$match:用于过滤数据,只输出符合条件的文档。$match使用MongoDB的标准查询操作。
$limit:用来限制MongoDB聚合管道返回的文档数。
$skip:在聚合管道中跳过指定数量的文档,并返回余下的文档。
$unwind:将文档中的某一个数组类型字段拆分成多条,每条包含数组中的一个值。
$group:将集合中的文档分组,可用于统计结果。
$sort:将输入文档排序后输出。
$geoNear:输出接近某一地理位置的有序文档
> db.sub.aggregate([{$group:{"_id":'$title',counter:{$sum:1}}}])
{ "_id" : "css", "counter" : 1 }
{ "_id" : null, "counter" : 3 }
{ "_id" : "js", "counter" : 1 }
{ "_id" : "python", "counter" : 1 }
{ "_id" : "c++", "counter" : 1 }
{ "_id" : "java", "counter" : 1 }

$match用于过滤数据,只显示符合条件的文档

> db.sub.find()
{ "_id" : ObjectId("5b7591b73a1d5dd1beb2b7aa"), "title" : "java" }
{ "_id" : ObjectId("5b7591d23a1d5dd1beb2b7ab"), "title" : "python" }
{ "_id" : ObjectId("5b759ade5591ee81f5f24108"), "title" : "c++" }
{ "_id" : ObjectId("5b759ae35591ee81f5f24109"), "title" : "js" }
{ "_id" : ObjectId("5b759ae75591ee81f5f2410a"), "title" : "css" }
{ "_id" : ObjectId("5b759ea05591ee81f5f2410b"), "price" : 12000 }
{ "_id" : ObjectId("5b759ea45591ee81f5f2410c"), "price" : 11000 }
{ "_id" : ObjectId("5b759eaa5591ee81f5f2410d"), "price" : 10000 }
> db.sub.aggregate([{$match:{'price':{$gt:10000}}}])
{ "_id" : ObjectId("5b759ea05591ee81f5f2410b"), "price" : 12000 }
{ "_id" : ObjectId("5b759ea45591ee81f5f2410c"), "price" : 11000 }

$project():修改输入文档的结构,如重命名,增加、删除字段、创建计算结果

例如:只显示counter,不显示id

> db.sub.aggregate([{$group:{"_id":'$title',counter:{$sum:1}}},{$project:{_id:0,counter:1}}])
{ "counter" : 1 }
{ "counter" : 3 }
{ "counter" : 1 }
{ "counter" : 1 }
{ "counter" : 1 }
{ "counter" : 1 }

$limit:限制聚合管道返回额文档数

> db.sub.find()
{ "_id" : ObjectId("5b7591b73a1d5dd1beb2b7aa"), "title" : "java" }
{ "_id" : ObjectId("5b7591d23a1d5dd1beb2b7ab"), "title" : "python" }
{ "_id" : ObjectId("5b759ade5591ee81f5f24108"), "title" : "c++" }
{ "_id" : ObjectId("5b759ae35591ee81f5f24109"), "title" : "js" }
{ "_id" : ObjectId("5b759ae75591ee81f5f2410a"), "title" : "css" }
{ "_id" : ObjectId("5b759ea05591ee81f5f2410b"), "price" : 12000 }
{ "_id" : ObjectId("5b759ea45591ee81f5f2410c"), "price" : 11000 }
{ "_id" : ObjectId("5b759eaa5591ee81f5f2410d"), "price" : 10000 }
> db.sub.aggregate([{$limit:2}])
{ "_id" : ObjectId("5b7591b73a1d5dd1beb2b7aa"), "title" : "java" }
{ "_id" : ObjectId("5b7591d23a1d5dd1beb2b7ab"), "title" : "python" }

$skip

> db.sub.aggregate([{$limit:2}])
{ "_id" : ObjectId("5b7591b73a1d5dd1beb2b7aa"), "title" : "java" }
{ "_id" : ObjectId("5b7591d23a1d5dd1beb2b7ab"), "title" : "python" }
> db.sub.aggregate([{$limit:2},{$skip:1}])
{ "_id" : ObjectId("5b7591d23a1d5dd1beb2b7ab"), "title" : "python" }

 $unwind:将文档中的某一个数组类型字段拆分成多条,每条包含数组中的一个值。

> db.t2.find()
{ "_id" : 1, "item" : "t-shirt", "size" : [ "S", "M", "L" ] }
> db.t2.aggregate([{$unwind:'$size'}])
{ "_id" : 1, "item" : "t-shirt", "size" : "S" }
{ "_id" : 1, "item" : "t-shirt", "size" : "M" }
{ "_id" : 1, "item" : "t-shirt", "size" : "L" }

 

posted on 2018-08-17 20:03  Mr.Hui  阅读(198)  评论(0编辑  收藏  举报

导航