1、为什么进行数据库设计?

良好的设计

糟糕的设计

减少数据冗余

存在大量数据冗余

避免数据维护异常

存在数据插入,删除,更新异常

节约存储空间

浪费存储空间

高效的访问

访问效率低

2、数据库设计步骤

数据库设计、分库分表

3、逻辑设计——三大范式

第一范式:强调的是列的原子性,即列不能够再分成其他几列。    

     --->字段不可分    

 第二范式:表必须有一个主键;没有包含在主键中的列必须完全依赖于主键,而不能只依赖于主键的一部分。    

      -->非主键字段依赖主键          

第三范式:非主键列必须直接依赖于主键,不能存在传递依赖。即不能存在:非主键列 A 依赖于非主键列 B,非主键列 B 依赖于主键的情况。      

      -->非主键字段不能互相依赖

数据库设计、分库分表

4、物理设计——反范式化

基本表及其字段之间的关系, 应尽量满足第三范式。但是,满足第三范式的数据库设计,往往不是最好的设计。 为了提高数据库的运行效率,常常需要降低范式标准:适当增加冗余,达到以空间换时间的目的。    

 eg:合理的冗余字段将会给我们减少join的查询        

         增加数据的读取效率

5、维护优化——分表

项目开发中,我们的数据库数据越来越大,随之而来的是单个表中数据太多。以至于查询速度变慢,而且由于表的锁机制导致应用操作也搜到严重影响,出现了数据库性能瓶颈。

当出现这种情况时,我们可以考虑分表,即将单个数据库表进行拆分,拆分成多个数据表, 然后用户访问的时候,根据一定的算法,让用户访问不同的表, 这样数据分散到多个数据表中,减少了单个数据表的访问压力。 提升了数据库访问性能。

在分表之前, 首先要选中合适的分表策略(以哪个字段为分表字段,需要将数据分为多少张表), 使数据能够均衡的分布在多张表中,并且不影响正常的查询。

垂直拆分是根据业务将一个库(表)拆分为多个库(表)

水平拆分则是根据分片算法将一个库(表)拆分为多个库(表)

①水平分表:降低在查询时需要读的数据和索引的页数 适用场景:表中的数据本身就有独立性,例如表中分表记录各个地区的数据或者不同时期的数据,特别是有些数据常用,有些不常用。 解决:单表中数据量增长出现的压力

②垂直分表:把主键和一些列放在一个表,然后把主键和另外的列放在另一个表中  适用场景:一个表中某些列常用,另外一些列不常用;可以使数据行变小,一个数据页能存储更多数据,查询时减少I/O次数;  把不同的业务模块分成不同的数据表,这些业务模块直接最好是0耦合 不解决问题:单表中数据量增长出现的压力 查询时会减少I/O次数

 

水平分表

垂直分表

优点

不存在单库大数据,高并发的性能瓶颈

提高了系统的稳定性跟负载能力

拆分后业务清晰,拆分规则明确 

系统之间整合或扩展容易 

 数据维护简单

缺点

拆分规则难以抽象

事务一致性难以解决

数据多次扩展难度跟维护量极大

 

 

部分业务表无法 join

受业务不同的限制存在单库性能瓶颈,不易数据扩展跟性能提高

事务处理复杂 

存在单表读写与存储瓶颈

 

 

策略:取模              枚举            区间范围            时间 (月)

6、维护优化——分库

分表能够解决单表数据量过大带来的查询效率下降的问题, 但是,却无法给数据库的并发处理能力带来质的提升。 面对高并发的读写访问,当数据库master服务器无法承载写操作压力时,不管如何扩展slave服务器,此时都没有意义了。

因此,我们必须换一种思路,对数据库进行拆分,从而提高数据库写入能力,这就是所谓的分库。 与分表策略相似,分库可以采用通过一个关键字取模的方式,来对数据访问进行路由

 

7. 分库分表有哪些问题

1.事务问题: 在执行分库分表之后,由于数据存储到了不同的库上,数据库事务管理出现了困难

 

优点

缺点

方案一:使用分布式事务

 

交由数据库管理,简单有效

 

性能代价高

 

方案二:由应用程序和数据库共同控制

性能上有优势

形成程序逻辑上的事务,又会造成编程方面的负担

2.跨库join问题: 在执行分库分表之后,难免会将原来逻辑性很强的数据划分到不同的表/库上,这时,表的关联操作将收到限制,无法join操作    

方案:将操作分成多步完成。在第一次查询的结果集中找出关联数据的id,根据这些id发起第二次请求得到关联数据。

8、sharding-jdbc分表算法

数据库设计、分库分表

实现了一个精准分片的算法,doSharding方法,里面包含两个参数availableTargetNames和shardingValue。 preciseShardingValue------------->分表字段,比如data_type;

availableTargetNames------------->实际数据库表节点 当分表字段满足一定的条件时,返回实际数据库表节点

数据库设计、分库分表

actual-data-nodes:真实数据节点,由数据源名 + 表名组成,以小数点分隔;多个表以逗号分隔

sharding-column :分表字段

 

相关文章:

  • 2021-12-10
  • 2021-07-10
  • 2021-06-25
猜你喜欢
  • 2022-02-20
  • 2021-11-24
  • 2021-07-24
  • 2021-08-02
  • 2021-11-16
  • 2021-10-28
  • 2022-02-05
相关资源
相似解决方案