MongoDB_基础知识
mongoDB术语:database-数据库,collection-数据库表/集合,document-数据记录行/文档,field-数据字段/域,index-索引,primary key-主键(MongoDB自动将_id字段设置为主键)
文档
文档是MongoDB的核心概念,文档就是键值对的一个有序集{'msg':'hello','foo':'2'},类似于python中的有序字典
需要注意: 文档中的键/值对是有序的 文档中的值不仅可以是在双引号里面的字符串,还可以是其他几种数据类型(甚至可以是整个嵌入的文档) MongoDB区分类型和大小写 MongoDB的文档不能有重复的键 文档中的值可以是多种不同的数据类型,也可以是一个完整的内嵌文档。文档的键是字符串,除了少数例外情况,键可以使用任意UTF-8字符 文档键命名规范: 键不能含有\0(空字符),这个字符用来表示键的结尾 .和$有特别的意义,只有在特定环境下才能使用 以下划线_开头的键是保留的(不是严格要求的)
集合
集合就是一组文档。
集合存在于数据库中,集合没有固定的结构,这意味着我们可以把不同格式和类型的数据放入一个集合中。
组织子集合的方式就是使用'.',分隔不同命名空间的子集合。
比如一个具有博客功能的应用可能包含两个集合,分别是blog.posts和blog.authors,这是为了使组织结构更清晰,这里的blog集合(这个集合甚至不需要存在)跟它的两个子集合没有任何关系。 在MongoDB中,使用子集合来组织数据非常高效,值得推荐
当第一个文档插入时,集合就会被创建
合法的集合名 集合名不能是空字符串" " 集合名不能还有\0字符(空字符),这个字符表示集合名的结尾 集合名不能以“system.”开头,这是为系统集合保留的前缀 用户创建的集合名字不能含有保留字符,有些驱动程序的确支持在集合名里面包含,这是因为某些系统生成的集合中包含该字符,除非你要访问这种系统创建的集合,否则千万不要在名字里出现$
数据库
在MongoDB中,多个文档组成集合,多个集合可以组成数据库。
数据库也可以通过名字来标识,数据库名可以是满足以下条件的任意UTF-8字符串
不能是空字符串("") 不得含有' '(空格),'.','$','/','\','\0(空字符)' 应全部小写 最多64字节
有些数据库名是保留的,可以直接访问这些有特殊作用的数据库
admin:从身份认证的角度讲,这是"root"数据库,如果将一个用户添加到admin数据库,这个用户将自动获得所有数据库的权限。再者,一些特定的服务器端命令也只能从admin数据库运行,如列出所有数据库或关闭服务器 local:这个数据库永远都不可以复制,且一台服务器上的所有本地集合都可以存储在这个数据库中 config:MongoDB用于分片设置时,分片信息会存储在config数据库中
命名空间
把数据库名添加到集合名前,得到集合的完全限定名,即命名空间
例如: 如果要使用cms数据库中的blog.posts集合,这个集合的命名空间就是 cmd.blog.posts。命名空间的长度不得超过121个字节,且在实际使用中应该小于100个字节
基本数据类型
#1、null:用于表示空或不存在的字段 d={'x':null} #2、布尔型:true和false d={'x':true,'y':false} #3、数值 d={'x':3,'y':3.1415926} #4、字符串 d={'x':'egon'} #5、日期 d={'x':new Date()} d.x.getHours() #6、正则表达式 d={'pattern':/^egon.*?nb$/i} #正则写在//内,后面的i代表: i 忽略大小写 m 多行匹配模式 x 忽略非转义的空白字符 s 单行匹配模式 #7、数组 d={'x':[1,'a','v']} #8、内嵌文档 user={'name':'egon','addr':{'country':'China','city':'YT'}} user.addr.country #9、对象id:是一个12字节的ID,是文档的唯一标识,不可变 d={'x':ObjectId()}
MongoDB中存储的文档必须有一个"_id"键。这个键的值可以是任意类型,默认是个ObjectId对象。 在一个集合里,每个文档都有唯一的“_id”,确保集合里每个文档都能被唯一标识。 不同集合"_id"的值可以重复,但同一集合内"_id"的值必须唯一 #1、ObjectId ObjectId是"_id"的默认类型。因为设计MongoDb的初衷就是用作分布式数据库,所以能够在分片环境中生成唯一的标识符非常重要,而常规的做法:在多个服务器上同步自动增加主键既费时又费力,这就是MongoDB采用ObjectId的原因。 ObjectId采用12字节的存储空间,是一个由24个十六进制数字组成的字符串 0|1|2|3| 4|5|6| 7|8 9|10|11 时间戳 机器 PID 计数器 如果快速创建多个ObjectId,会发现每次只有最后几位有变化。另外,中间的几位数字也会变化(要是在创建过程中停顿几秒)。这是ObjectId的创建方式导致的,如上图 时间戳单位为秒,与随后5个字节组合起来,提供了秒级的唯一性。这个4个字节隐藏了文档的创建时间,绝大多数驱动程序都会提供一个方法,用于从ObjectId中获取这些信息。 因为使用的是当前时间,很多用户担心要对服务器进行时钟同步。其实没必要,因为时间戳的实际值并不重要,只要它总是不停增加就好。 接下来3个字节是所在主机的唯一标识符。通常是机器主机名的散列值。这样就可以保证不同主机生成不同的ObjectId,不产生冲突 接下来两个字节确保了在同一台机器上并发的多个进程产生的ObjectId是唯一的 前9个字节确保了同一秒钟不同机器不同进程产生的ObjectId是唯一的。最后3个字节是一个自动增加的计数器。确保相同进程的同一秒产生的ObjectId也是不一样的。 #2、自动生成_id 如果插入文档时没有"_id"键,系统会自帮你创建 一个。可以由MongoDb服务器来做这件事。 但通常会在客户端由驱动程序完成。这一做法非常好地体现了MongoDb的哲学:能交给客户端驱动程序来做的事情就不要交给服务器来做。 这种理念背后的原因是:即便是像MongoDB这样扩展性非常好的数据库,扩展应用层也要比扩展数据库层容易的多。将工作交给客户端做就减轻了数据库扩展的负担。