在使用mongodb之前先了解一些mongodb的一些基础概念
- 文档: MongoDB 中的基本数据单元,相当于关系数据库管理系统中的行。每个文档都有一个特殊的键 “_id”,其在所属的集合中是唯一的。
- 集合:具有动态模式的表。
- mongo shell:对管理 MongoDB 实例和使用 MongoDB 的查询语言操作数据提供了内置的支持。它也是一个功能齐全的JavaScript 解释器,用户可以根据需求创建或加载自己的脚本。
为了更好地理解mongodb中的概念,以下是关系型数据库和mongodb的一些名词的对比:
文档是一组有序键值的集合。在JavaScript 中,文档表示为对象:
{"greeting" : "Hello, world!", "views" : 3}
文档中的键是字符串类型。除了少数例外的情况,可以使用任意 UTF-8 字符作为键。
- 键中不能含有 \0(空字符)。这个字符用于表示一个键的结束。
- . 和 $ 是特殊字符,只能在某些特定情况下使用。可以认为这两个字符属于保留字符,如果使用不当,那么驱动程序将无法正常工作。
- 集合名称不能以system.开头,该前缀是为内部集合保留的。
文档区分类型和大小写。例如,下面是不同的:
{"count" : 5}
{"count" : "5"}
{"count" : 5}
{"Count" : 5}
文档不能包含重复的键。例如,下面这个文档是不合法的。
{"greeting" : "Hello, world!", "greeting" : "Hello, MongoDB!"}
但文档和文档之间可以重复。
集合就是一组文档。如果将文档比作关系数据库中的行,那么一个集合就相当于一张表。
动态模式是指在一个集合中,文档之间的(字段、类型列表)不必一致,比如如下两个文档:
{"greeting" : "Hello, world!", "views": 3}
{"signoff": "Good night, and good luck"}
动态模式的原因:ing
在集合中获取文档本身要比提取集合的文档类型列表要快的多。设一个集合中每个文档都有一个"filed1"字段来指明文档是"A",“B"还是"C”,在当个集合中查找这三个值要比找到3个相应的集合慢的多。
使用 . 字符分隔不同命名空间的子集合。
例如,有一个具有博客功能的应用程序,可能包含名为blog.posts 和名为 blog.authors 的集合。这只是一种组织管理的方式,blog 集合(它甚至不必存在)与其“子集合”之间没有任何关系。
数据库名称可以是任意 UTF-8 字符串,但有以下限制。
- 数据库名称不能是空字符串(“”)。
- 数据库名称不能包含 /、\、.、"、*、<、>、:、|、?、$、单一的空格以及 \0(空字符),基本上只能使用 ASCII 字母和数字。
- 数据库名称区分大小写。
- 数据库名称的长度限制为 64 字节。
admin
admin 数据库会在身份验证和授权时被使用。此外,某些管理操作需要访问此数据库。
local
特定于单个服务器的数据会存储在此数据库中。在副本集中,local 用于存储复制过程中所使用的数据,而 local 数据库本身不会被复制。
config
MongoDB 的分片集群会使用 config 数据库存储关于每个分片的信息。
命名空间是指:通过将数据库名称与该库中的集合名称连接起来,可以获得一个完全限定的集合名称。
例子:
如果你要使用 cms 数据库中的 blog.posts 集合,则该集合的命名空间为cms.blog.posts。
命名空间的长度限制为 120 字节,而实际使用时应该小于 100 字节。
MongoDB 中的文档可以被认为是“类似于 JSON”的形式,因为它们在概念上和 JavaScript 中的对象非常相近。
json表达的局限性:
- JSON 只有 null、布尔值、数字、字符串、数组和对象这几种类型;
- 例如,JSON 没有日期类型,这使得原本容易的日期处理变得很麻烦;
- JSON 只有一个数字类型,因此没有办法区分浮点数和整数,更不用说区分 32 位和 64 位的数字了。同样,JSON 也无法表示其他的常用类型,比如正则表达式或函数。
MongoDB 在保留了 JSON 基本键–值对特性的基础上,增加了对许多额外数据类型的支持。
序号 | 字段类型 | 举例说明 |
---|---|---|
1 | null类型 | 用于表示空值或不存在的字段。{"x" : null} |
2 | 布尔类型 | 值可以为 true 或者 false。{"x" : true} |
3 | 数值类型 | shell 默认使用 64 位的浮点数来表示数值类型。{"x" : 3.14} {"x" : 3} |
4 | 整数类型 | 使用 NumberInt/NumberLong 类,分别表示 4/8 字节的有符号整数。{"x" : NumberInt("3")} {"x" : NumberLong("3")} |
5 | 字符串类型 | 任何 UTF-8 字符串都可以使用字符串类型来表示。{"x" : "foobar"} |
6 | 日期类型 | 1. MongoDB 会将日期存储为 64 位整数,表示自 Unix 纪元(1970 年 1 月 1 日)以来的毫秒数,不包含时区信息。 2. 时区信息可以存储为另一个键的值。 {"x" : new Date()} |
7 | 数组类型 | 集合或者列表可以表示为数组。{"x" : ["a", "b", "c"]} |
8 | 内嵌文档 | {"x" : {"foo" : "bar"}} |
9 | Object ID | Object ID 是一个 12 字节的 ID,是文档的唯一标识。{"x" : ObjectId()} |
10 | 二进制数据 | 二进制数据是任意字节的字符串,不能通过 shell 操作。如果要将非 UTF-8 字符串存入数据库,那么使用二进制数据是唯一的方法。 |
11 | 代码 | MongoDB 还可以在查询和文档中存储任意的JavaScript 代码 |
接着对一些复杂的数据类型进行进一步的说明
文档中的数组有一个非常好的特性,就是 MongoDB 能够“理解”其结构,并且知道如何深入数组内部对其内容执行操作。这允许我们对数组进行查询并使用其内容创建索引。
例如:
MongoDB 可以查询出 “things” 数组中包含3.14 这个元素的所有文档。
如果这是一个经常会使用的查询,那么你甚至可以对 “things” 这个键创建索引来提高查询速度。
{"x" : ["a", "b", "c"]}
数组可以包含不同数据类型的元素
{"things" : ["pie", 3.14]}
文档可以嵌套其他文档,此时被嵌套的文档就成了父文档的值,这称为内嵌文档。
{"x" : {"foo" : "bar"}}
与数组一样,MongoDB“理解”内嵌文档的结构,并能够在其中创建索引、执行查询或进行更新。
但需要注意的是
MongoDB 可能会导致更多的数据重复:
假设addresses 是关系数据库中一个单独的表,我们需要修正地址中的一个拼写错误。当对 people 和 addresses 进行连接操作时,每个共享此地址的人的信息都会得到更新;
使用MongoDB,则需要对每个人的文档中的这个拼写错误分别进行修正。
ObjectId 是 “_id” 的默认类型。ObjectId 类采用了轻量化设计,可以很容易地在不同的机器上以全局唯一的方式生成。
注意:
MongoDB 的分布式特性是它使用 ObjectId 而不是其他传统做法(比如自动递增主键)的主要原因:跨多个服务器同步自动递增主键既困难又耗时。
ObjectId 占用了 12 字节的存储空间,可以用 24 个十六进制数字组成的字符串来表示:每字节存储两个数字。
参考:中文官网