SQL VS NoSQL 如何选择数据库

前一篇文章中我们主要的讨论了SQL与NoSQL数据库之间的主要的差别。接下来,我们将会利用上一篇中的知识来确定在特定的场景中如何确定比较好的选择。

首先我们先来总结一下:

SQL数据库:

  • ?使用表存储相关的数据
  • 在使用表之前需要先定义标的模式
  • 鼓励使用规范化来减少数据的冗余
  • 支持使用JION操作,使用一条SQL语句从多张表中取出相关的数据
  • 需要满足数据完整性约束规则
  • 使用事务来保证数据的一致性
  • 能够大规模的使用
  • 使用强大的SQL语言进行查询操作
  • 提供大量的支持,专业技能和辅助工具

NoSQL数据库:

  • 使用类JOSN格式的文档来存储键值对信息
  • 存储数据不需要特定的模式
  • 使用非规范化的标准存储信息,以保证一个文档中包含一个条目的所有信息
  • 不需要使用JION操作
  • 允许数据不用通过验证就可以存储到任意的位置
  • 保证更新的单个文档,而不是多个文档
  • 提供卓越的性能和可扩展性
  • 使用JOSN数据对象进行查询
  • 是一种新型的技术

SQL数据库适合那些需求确定和对数据完整性要去严格的项目。NoSQL数据库适用于那些对速度和可扩展性比较看重的那些不相关的,不确定和不断发展的需求。简单来说就是:

  • SQL是精确的。它最适合于具有精确标准的定义明确的项目。典型的使用场景是在线商店和银行系统。
  • NoSQL是多变的。它最适合于具有不确定需求的数据。典型的使用场景是社交网络,客户管理和网络分析系统。

很少有项目能够很好的适用于一种数据库。如果你对数据的需求比较小或是非标准化的数据任何一种数据库都是可以的。你比我更了解你的项目,我不建议你将SQL上的数据移植到NoSQL上反之亦然,除非它能够提供非常可观的收益。当然选择权在于你自己。在项目的一开始就要考虑好使用它们的利弊,这样才不会导致选择错误。

场景一:通讯记录

我们来重新的定义操作并基于SQL实现通讯录系统。我们初始简单的定义contact表拥有如下几个字段;

  • id
  • title
  • firstname
  • lastname
  • gender
  • telephone
  • email
  • address1
  • address2
  • address3
  • city
  • region
  • zipcode
  • country

问题一:很少有人只拥有一个手机号。或许我们可以再添加三个字段:固定电话,移动电话和工作电话,但是无论我们给一个联系人分配了多少个字段总会有人需要更多。我们需要创建一个单独的telephone表,这样就可以给一个联系人存多个号码了。这样也就规范化了我们的数据— 我们不需要一个没有电话的联系人:

  • contact_id
  • name (说明字段:固定,工作,私人等.)
  • number

问题二:对于联系人邮箱我们也会遇到上述问题,因此我们也需要创建一个email的表:

  • contact_id
  • name (说明字段:固定,工作,私人等.)
  • address

问题三:我们在填写联系人信息是我们并不希望填写他的地理位置,或者我们想记录他工作、生活、旅游的地方等。因此我们需要一个address表:

  • contact_id
  • name (text such as home, office, etc.)
  • address1
  • address2
  • address3
  • city
  • region
  • zipcode
  • country

我们原先设计的contact表就精简为:

  • id
  • title
  • firstname
  • lastname
  • gender

好了,我们已经设计了一个规范化的数据库,可以用来存储任何一个联系人的电话号码,邮箱地址和住址了。但是......

模式是固定不变的

我们并没有考虑到联系人的生日,公司或者职位。不管我们添加多少个字段,我们会得到更多的需求:备注,周年纪念日,关系,社交账号,喜欢巧克力的种类等等。预测每一个需求对于我们来说是非常困难的,因此我们需要创建一张表其中存储的形式是键值对来应对不断增加的需求。

数据是碎片化的

对于开发人员和系统管理员来说不断地检查数据库是比较麻烦的。程序的逻辑会变得更复杂效率更慢,因为使用一条select语句来JOIN多个表来取出一个联系人的全部信息不太实际。(当然这也是可以实现的,但是当一个联系人中国包含电话号码,邮件地址和住址信息时:如果一个人有3个电话号码,五个邮箱和两个住址,那么SQL查询会产生30个结果,也就是说说这样的效率会很慢。)

最后,全文搜索是非常困难的。如果一个人要查询一个字符型:favorite,我们需要依次查询上述的四张表判断是否是一个联系人的姓名,电话,邮件或者地址依据这些把结果进行排序。如果你使用过WordPress的搜索,你就会发现是都么的烦人了!

使用NoSQL来替代SQL

我们的联系人关注的是人这个实体。然而关于人的信息是不可预测的并且在不同的阶段的需求也会不一样。如果我们使用NoSQL数据库会比较方便,NoSQL将一个人的信息存储为一个文档并放入contacts的集合中:

{
  name: [
    "Billy", "Bob", "Jones"
  ],
  company: "Fake Goods Corp",
  jobtitle: "Vice President of Data Management",
  telephone: {
    home: "0123456789",
    mobile: "9876543210",
    work: "2244668800"
  },
  email: {
    personal: "[email protected]",
    work: "[email protected]"
  },
  address: {
    home: {
      line1: "10 Non-Existent Street",
      city: "Nowhere",
      country: "Australia"
    }
  },
  birthdate: ISODate("1980-01-01T00:00:00.000Z"),
  twitter: ‘@bobsfakeaccount‘,
  note: "Don‘t trust this guy",
  weight: "200lb",
  photo: "52e86ad749e0b817d25c8892.jpg"
}

在这个示例中,我们没有存储这个人的性别和职衔,并且可以添加一些别的联系人没用的信息。在NoSQL中这样的存储是合法的,并且我们可以按照各人的意愿来添加和删除一个字段。

因为一个联系人存储在一个文档中,因此我们可以使用一个查询语句取出一个人的所有信息。对于全文搜索,在MongoDB中我们可以在contact的字段中定义一个索引:

db.contact.createIndex({ "$**": "text" });

然后我们就可以使用如下的语句进行全文搜索:

db.contact.find({
  $text: { $search: "something" }
});

场景二:社交网络

一个典型的社交网络使用的联系人的信息是相似,但是也会增加一些新的功能例如:社交网络,状态更新,私信和点赞。这些功能会根据用户的需求进行添加或者删除,预测用户的需求对开发人员来说是非常困难的。

另外:

  • 大多数的更新都有一个原始的出发点:用户。但是,对于开发人员来说一次性的把所有的回馈都进行更新是不可能的。
  • 不管用户怎么想,一个失败的版本并可能造成太大的经济损失。一个应用的接口设计和功能表现是比数据的完整性的优先级要高。

因此,NoSQL是一个不错的选择。数据库允许我们存储不同类型的数据以便于我们快速的开发出新的功能。例如,因为所有的数据状态的更新都可以在status的集合中的一个文档中进行:

{
  user_id: ObjectID("65f82bda42e7b8c76f5c1969"),
  update: [
    {
      date: ISODate("2015-09-18T10:02:47.620Z"),
      text: "feeling more positive today"
    },
    {
      date: ISODate("2015-09-17T13:14:20.789Z"),
      text: "spending far too much time here"
    }
    {
      date: ISODate("2015-09-17T12:33:02.132Z"),
      text: "considering my life choices"
    }
  ]
}

尽管对于这个文档来说数据会变得多一些,但是我们可以仅仅取出文档的一个子集,例如:最新的状态等。对于每一个用户来说历史记录也会很容易搜索的到。

场景三:仓库管理系统

现在,我们来分析一下一个仓库的管理系统。我们需要记录如下的信息:

  • 货物入库的信息和存放的位置信息
  • 货物在仓库中的移动,例如:为相同的货物分配相邻的位置存放
  • 货物的摆放顺序以及配送货物之后的一系列问题。

数据需求:

  1. 保存货物的基本信息例如:尺寸、大小、颜色等,这些不相关的数据我们要能够用到任何的货物上。我们不可能去考虑一些货物个性化的信息例如:笔记本处理器的速度或者是一部手机电池的寿命。
  2. 我们要尽可能的避免错误的发生。我们不能让货物凭空消失或者将货物存放到已经存放货物的位置上去。
  3. 以更加简单的方式操作。我们记录将一件货物从一个位置移动到另一个位置或者从A移动到B的操作是相同的。

因此,我们需要考虑对数据的完整性和对于事务的支持。目前来说也就是SQL能够很好地满足我们的需求。

总结

我希望上述的案例能够对你有一定的帮助,但是每一个实际的项目都是不同的,对一无二的你需要自己去做决定选择一种适合的。(尽管,对于我们开发人员来说我们不太愿意去改变我们现有的选择,无论新的技术有多好!O(∩_∩)O)

建议:去尝试了解更多新的技术。这样我们就可以非常有理由的选择一种数据库进行开发。祝你好运!

时间: 2024-10-15 22:09:30

SQL VS NoSQL 如何选择数据库的相关文章

SQL与NoSQL(关系型与非关系型)数据库的区别

永远正确的经典答案依然是:具体问题具体分析. 数据表VS.数据集 关系型和非关系型数据库的主要差异是数据存储的方式.关系型数据天然就是表格式的,因此存储在数据表的行和列中.数据表可以彼此关联协作存储,也很容易提取数据.与其相反,非关系型数据不适合存储在数据表的行和列中,而是大块组合在一起.非关系型数据通常存储在数据集中,就像文档.键值对或者图结构.你的数据及其特性是选择数据存储和提取方式的首要影响因素. 预定义结构VS.动态结构 关系型数据通常对应于结构化数据,因为数据表都有预定义好的结构(列的

SQL or NoSQL? 从存储的架构演进看数据库选型

一.前言 你是否在为系统的数据库来一波大流量就几乎打满CPU,日常CPU居高不下烦恼?你是否在各种NoSQL间纠结不定,到底该选用哪种最好?今天的你就是昨天的我,这也是写这篇文章的初衷. 这篇文章是我好几个月来一直想写的一篇文章,也是一直想学习的一个内容,作为互联网从业人员,我们要知道关系型数据库(MySQL.Oracle)无法满足我们对存储的所有要求,因此对底层存储的选型,对每种存储引擎的理解非常重要.同时也由于过去一段时间的工作经历,对这块有了一些更多的思考,想通过自己的总结把这块写出来分享

大数据入门级学习:SQL与NOSQL数据库

这几年的大数据热潮带动了一激活了一大批hadoop学习爱好者.有自学hadoop的,有报名培训班学习的.所有接触过hadoop的人都知道,单独搭建hadoop里每个组建都需要运行环境.修改配置文件测试等过程.对于我们这些入门级新手来说简直每个都是坑.国内的发行版hadoop那么多,似乎都没有来填这样的坑?不知道是没法解决,还是没有想到?安装运行环境这样的坑,那些做国产大数据底层开发的,如果不能解决这个问题的话,我觉得不是一个合格的大数据底层开发机构.不过比较幸运的是,三月的时候申请拿到了一个DK

SQL VS NoSQL

(关系型与非关系型)数据库的区别: 关系型和非关系型数据库的主要差异是数据存储的方式 1.1 数据表 VS 数据集 关系型数据天然就是表格式的,因此存储在数据表的行和列中.数据表可以彼此关联协作存储,也很容易提取数据.与其相反,非关系型数据不适合存储在数据表的行和列中,而是大块组合在一起.非关系型数据通常存储在数据集中,就像文档.键值对或者图结构 1.2 预定义结构 VS 动态结构 关系型数据通常对应于结构化数据,因为数据表都有预定义好的结构(列的定义),结构描述了数据的形式和内容.这一点对数据

SQL vs NoSQL 没有硝烟的战争!

声明:本文译自SQL vs NoSQL The Differences,如需转载请注明出处. SQL(结构化查询语言)数据库作为一个主要的数据存储机制已经超过40个年头了.随着web应用和像MySQL.PostgreSQL和SQLite这些开源项的兴起,SQL使用量大大增加. NoSQL数据库在20世纪60年代就已经出现了,但最近因为MongoDB.CouchDB,Redis和Apache Cassandra等才受到广泛的关注. 你会发现很多教程都会解释如何根据你的兴趣选择去使用SQL还是NoS

十六款值得关注的NoSQL与NewSQL数据库--转载

原文地址:http://tech.it168.com/a2014/0929/1670/000001670840_all.shtml [IT168 评论]传统关系型数据库在诞生之时并未考虑到如今如火如荼的移动.社交以及大数据负载类型,同时也并不适合处理极端规模处理任务.不过大家不必担心,十六家专业企业已经为我们带来他们各自的次世代NoSQL与NewSQL选项. 为什么在处理全新数据类型以及极端业务规模实例时,企业正越来越多地选择备用方案来替代占据领导地位的关系型数据库管理系统(简称RDMS)? 带

SQL Server 2008 R2 附加数据库 “尝试打开或创建物理文件 拒绝访问”的解决办法

其实是来自一篇SQL Server 2005同样错误的帖子,不过试了在SQL Server 2008 R2下面也有效,记录一下. 解决方法: 在所有程序—Microsoft SQL Server 2008 R2—配置工具—SQL Server 配置管理器,点击"SQL Server 服务",右边会显示正在运行的服务,以及对应的用户,右击SQL Server (MSSQLSERVER),选择“属性”,把内置帐户选择为"Local System",点击重新启动就OK了.

NoSQL与关系型数据库比较

虽然09年出现了比较激进的文章<关系数据库已死>,但是我们心里都清楚,关系数据库其实还活得好好的,你还不能不用关系数据库.但是也说明了一个事实,关系数据库在处理WEB2.0数据的时候,的确已经出现了瓶颈. 那么我们到底是用NoSQL还是关系数据库呢?我想我们没有必要来进行一个绝对的回答.我们需要根据我们的应用场景来决定我们到底用什么. 如果关系数据库在你的应用场景中,完全能够很好的工作,而你又是非常善于使用和维护关系数据库的,那么我觉得你完全没有必要迁移到NoSQL上面, 除非你是个喜欢折腾的

使用SQL Server Management Studio 创建数据库备份作业

SQL Server 作业无非就是按照规定的时间执行指定的脚本,这里介绍如何用SSMS(SQL Sever 2008)创建作业备份数据库. (0)假设在创建作业之前你所要备份的数据库已经存在:其次,你已经会启动SQL Sever 代理(一般是关闭的) (1)创建SQL Server代理作业 (1.1)新建作业,输出常规信息 如上图:输入作业名称(如:BackupJobTest),这里所有者和类别都是默认的,输入说明(就跟写代码要写注释一样,利人利己) (1.2)设置作业执行步骤 点击左边“选择页