数据库学习之(3)简单介绍数据库的水平切分与垂直切分

一、数据切分的概念:

  指通过某种特定的条件,将我们存放在同一个数据库中的数据分散存放到多个数据库(主机)上,以达到分散单台设备负载的效果。数据的切分同时还可以提高系统的总体可用性,因为单台设备Crash之后,只有总体数据的某部分不可用,而不是所有的数据。

  数据的切分(Sharding)根据其切分规则的类型,可以分为两种切分模式。一种是按照不同的表(或者Schema)来切分到不同的数据库(主机)之上,这种切可以称之为数据的垂直(纵向)切分;另外一种则是根据表中的数据的逻辑关系,将同一个表中的数据按照某种条件拆分到多台数据库(主机)上面,这种切分称之为数据的水平(横向)切分.

  垂直切分的最大特点就是规则简单,实施也更为方便,尤其适合各业务之间的耦合度非常低,相互影响很小,业务逻辑非常清晰的系统。在这种系统中,可以很容易做到将不同业务模块所使用的表分拆到不同的数据库中。根据不同的表来进行拆分,对应用程序的影响也更小,拆分规则也会比较简单清晰。

  水平切分于垂直切分相比,相对来说稍微复杂一些。因为要将同一个表中的不同数据拆分到不同的数据库中,对于应用程序来说,拆分规则本身就较根据表名来拆分更为复杂,后期的数据维护也会更为复杂一些。

  当我们某个(或者某些)表的数据量和访问量特别的大,通过垂直切分将其放在独立的设备上后仍然无法满足性能要求,这时候我们就必须将垂直切分和水平切分相结合,先垂直切分,然后再水平切分,才能解决这种超大型表的性能问题。

二、数据的垂直切分:

  我们先来看一下,数据的垂直切分到底是如何一个切分法的。数据的垂直切分,也可以称之为纵向切分。将数据库想象成由很多个一大块一大块的“数据块”(表)组成,我们垂直的将这些“数据块”切开,然后将他们分散到多台数据库主机上面。这样的切分方法就是一个垂直(纵向)的数据切分。
  一个架构设计较好的应用系统,其总体功能肯定是由很多个功能模块所组成的,而每一个功能模块所需要的数据对应到数据库中就是一个或者多个表。而在架构设计中,各个功能模块相互之间的交互点越统一,系统的耦合度就越低,系统各个模块的维护性以及扩展性也就越好。这样的系统,实现数据的垂直切分也就越容易。
  当我们的功能模块越清晰,耦合度越低,数据垂直切分的规则定义也就越容易。完全可以根据功能模块来进行数据的切分,不同功能模块的数据存放于不同的数据库主机中,可以很容易就避免掉跨数据库的Join存在,同时系统架构也非常的清晰。
  当然,很难有系统能够做到所有功能模块所使用的表完全独立,完全不需要访问对方的表或者需要两个模块的表进行Join操作。这种情况下,我们就必须根据实际的应用场景进行评估权衡。决定是迁就应用程序将需要Join的表的相关某快都存放在同一个数据库中,还是让应用程序做更多的事情,也就是程序完全通过模块接口取得不同数据库中的数据,然后在程序中完成Join操作。
  一般来说,如果是一个负载相对不是很大的系统,而且表关联又非常的频繁,那可能数据库让步,将几个相关模块合并在一起减少应用程序的工作的方案可以减少较多的工作量,是一个可行的方案。
  当然,通过数据库的让步,让多个模块集中共用数据源,实际上也是简洁的默许了各模块架构耦合度增大的发展,可能会让以后的架构越来越恶化。尤其是当发展到一定阶段之后,发现数据库实在无法承担这些表所带来的压力,不得不面临再次切分的时候,所带来的架构改造成本可能会远远大于最初的时候。
  所以,在数据库进行垂直切分的时候,如何切分,切分到什么样的程度,是一个比较考验人的难题。只能在实际的应用场景中通过平衡各方面的成本和收益,才能分析出一个真正适合自己的拆分方案。

垂直切分的优点:
◆ 数据库的拆分简单明了,拆分规则明确;
◆ 应用程序模块清晰明确,整合容易;
◆ 数据维护方便易行,容易定位;
垂直切分的缺点:
◆ 部分表关联无法在数据库级别完成,需要在程序中完成;
◆ 对于访问极其频繁且数据量超大的表仍然存在性能瓶颈,不一定能满足要求;
◆ 事务处理相对更为复杂;
◆ 切分达到一定程度之后,扩展性会遇到限制;
◆ 过读切分可能会带来系统过度复杂而难以维护。
  针对于垂直切分可能遇到数据切分及事务问题,在数据库层面实在是很难找到一个较好的处理方案。实际应用案例中,数据库的垂直切分大多是与应用系统的模块相对应,同一个模块的数据源存放于同一个数据库中,可以解决模块内部的数据关联问题。而模块与模块之间,则通过应用程序以服务接口方式来相互提供所需要的数据。虽然这样做在数据库的总体操作次数方面确实会有所增加,但是在系统整体扩展性以及架构模块化方面,都是有益的。可能在某些操作的单次响应时间会稍有增加,但是系统的整体性能很可能反而会有一定的提升。而扩展瓶颈问题,就只能依靠数据水平切分架构来解决了。

三、数据的水平切分:

  上面一节分析介绍了数据的垂直切分,这一节再分析一下数据的水平切分。数据的垂直切分基本上可以简单的理解为按照表、模块来切分数据,而水平切分就不再是按照表或者是功能模块来切分了。一般来说,简单的水平切分主要是将某个访问极其频繁的表再按照某个字段的某种规则来分散到多个表之中,每个表中包含一部分数据。
  简单来说,我们可以将数据的水平切分理解为是按照数据行的切分,就是将表中的某些行切分到一个数据库,而另外的某些行又切分到其他的数据库中。当然,为了能够比较容易的判定各行数据被切分到哪个数据库中了,切分总是都需要按照某种特定的规则来进行的。如根据某个数字类型字段基于特定数目取模,某个时间类型字段的范围,或者是某个字符类型字段的hash值。如果整个系统中大部分核心表都可以通过某个字段来进行关联,那这个字段自然是一个进行水平分区的上上之选了。
  一般来说,像现在互联网非常火爆的Web2.0类型的网站,基本上大部分数据都能够通过会员用户信息关联上,可能很多核心表都非常适合通过会员ID来进行数据的水平切分。而像论坛社区讨论系统,就更容易按照论坛编号来进行数据的水平切分。切分之后基本上不会出现各个库之间的交互。
  所以,对于我们的示例数据库来说,大部分的表都可以根据用户ID来进行水平的切分。不同用户相关的数据进行切分之后存放在不同的数据库中。如将所有用户ID通过2取模然后分别存放于两个不同的数据库中。每个和用户ID关联上的表都可以这样切分。这样,基本上每个用户相关的数据,都在同一个数据库中,即使是需要关联,也可以非常简单的关联上。

几种典型的分片规则包括:

  按照用户ID求模,将数据分散到不同的数据库,具有相同数据用户的数据都被分散到一个库中。

  按照日期,将不同月甚至日的数据分散到不同的库中。

  按照某个特定的字段求摸,或者根据特定范围段分散到不同的库中。

 水平切分优点:
◆ 表关联基本能够在数据库端全部完成;
◆ 不会存在某些超大型数据量和高负载、高并发的性能瓶颈问题,提高了系统的稳定性和负载能力;
◆ 应用程序端整体架构改动相对较少;
◆ 事务处理相对简单;
◆ 只要切分规则能够定义好,基本上较难遇到扩展性限制,join操作基本可以数据库做。
水平切分的缺点:
◆ 切分规则相对更为复杂,很难抽象出一个能够满足整个数据库的切分规则;

分片事务一致性难以解决;

跨库join性能较差;

◆ 后期数据的维护难度有所增加,人为手工定位数据更困难;

◆ 应用系统各模块耦合度较高,可能会对后面数据的迁移拆分造成一定的困难。

四、垂直与水平切分的联合使用:

  每一个应用系统的负载都是一步一步增长上来的,在开始遇到性能瓶颈的时候,大多数架构师和DBA都会选择先进行数据的垂直拆分,因为这样的成本最先,最符合这个时期所追求的最大投入产出比。然而,随着业务的不断扩张,系统负载的持续增长,在系统稳定一段时期之后,经过了垂直拆分之后的数据库集群可能又再一次不堪重负,遇到了性能瓶颈。

 联合切分的优点:

◆ 可以充分利用垂直切分和水平切分各自的优势而避免各自的缺陷;

◆ 让系统扩展性得到最大化提升;

联合切分的缺点:

◆ 数据库系统架构比较复杂,维护难度更大;

◆ 应用程序架构也相对更复杂。

数据源整合的两种解决思路:

1. 在每个应用程序模块中配置管理自己需要的一个(或者多个)数据源,直接访问各个数据库,在模块内完成数据的整合;

2. 通过中间代理层来统一管理所有的数据源,后端数据库集群对前端应用程序透明;(MyCat)

利用MySQLProxy实现数据切分及整合:

  MySQLProxy是MySQL官方提供的一个数据库代理层产品,和MySQLServer一样,同样是一个基于GPL开源协议的开源产品。可用来监视、分析或者传输他们之间的通讯信息。他的灵活性允许最大限度的使用它,目前具备的功能主要有连接路由,Query分析,Query过滤和修改,负载均衡,以及基本的HA机制等。
  MySQLProxy实际上是在客户端请求与MySQLServer之间建立了一个连接池。所有客户端请求都是发向MySQLProxy,然后经由MySQLProxy进行相应的分析,判断出是读操作还是写操作,分发至对应的MySQLServer上。对于多节点Slave集群,也可以起做到负载均衡的效果。以下是MySQLProxy的基本架构图:

五、针对数据切分后数据Join的难度处理经验:

第一原则:能不切分尽量不要切分。

第二原则:如果要切分一定要选择合适的切分规则,提前规划好。

第三原则:数据切分尽量通过数据冗余或表分组(Table Group)来降低跨库Join的可能。

第四原则:由于数据库中间件对数据Join实现的优劣难以把握,而且实现高性能难度极大,业务读取尽量少使用多表Join。

参考:https://blog.csdn.net/fly_as_tadpole/article/details/87870626

https://www.cnblogs.com/grefr/p/6088547.html

 

原文地址:https://www.cnblogs.com/Harriett-Lin/p/10789352.html