分布式数据库部署主要分为两种,一种是读写分离。这个需要弄主从数据库。主要是写的时候写主数据库,读的时候读从数据库。分散读取压力,对于读多写少的系统有利于

提高其性能。还有一种是分布式存储,这种主要是将一张表拆分成多张分表部署到各个服务器中,主要针对写操作频繁的系统,如微博,淘宝的订单系统。

这两种方案都会遇到主键类型及生成方式的问题,还有主从数据库不同步和主键冲突问题。

主键类型主要有GUID和数字类型,这里我们不讨论GUID;

数字主键主要存在唯一性、可同步性两个方面的不足

可同步性:可以不使用主键自增方案。

唯一性:可以单独使用存储过程生成ID,设置主键ID的初始值步长和最大值,及所对应的表,当然主从数据库的主表和分表初始值和最大值是不一样的,一样的话会造成主键重复。

存储过程:

-- ----------------------------
-- Procedure structure for getId
-- ----------------------------
DROP PROCEDURE IF EXISTS `getId`;
DELIMITER ;;
CREATE DEFINER=`sawyer`@`%` PROCEDURE `getId`(OUT aId INT, OUT aIdEnd INT, aType TINYINT)
BEGIN
DECLARE id,eid,iStep INT;
DECLARE rev TINYINT;
SELECT Current_ID,END,Step,REVERSE INTO id,eid,iStep,rev FROM t_id WHERE TYPE=aType;
IF id<eid THEN
SET aId = id;
IF id+iStep >= eid THEN
SET aIdEnd = eid;
IF rev = 1 THEN
UPDATE t_id SET Current_ID=Start_ID WHERE TYPE=aType;
ELSE
UPDATE t_id SET Current_ID=eid WHERE TYPE=aType;
END IF;
ELSE
SET aIdEnd = id+iStep;
UPDATE t_id SET Current_ID=aIdEnd WHERE TYPE=aType;
END IF;
ELSE
SET aId = 0, aIdEnd = 0;
END IF;
END
;;
DELIMITER ;

主表

从表

写一个java类去调用这个存储过程生成主键。

/*    */ package btir.dao.jdbc;
/* */
/* */ import btir.BtirException;
/* */ import btir.dao.ha.DBMgr;
/* */ import btir.dao.ha.PooledStmt;
/* */ import btir.utils.MiscUtil;
/* */ import org.apache.commons.logging.Log;
/* */ import org.apache.commons.logging.LogFactory;
/* */
/* */
/* */
/* */
/* */
/* */
/* */
/* */ public class IdHolder
/* */ {
/* */ public static final int NO_ID_AVAILABLE = 0;
/* 19 */ private static final Log log = LogFactory.getLog(IdHolder.class);
/* */
/* */
/* */
/* */ private int current;
/* */
/* */
/* */ private int end;
/* */
/* */
/* */
/* */ public synchronized int getId(byte type, int stmtId)
/* */ {
/* 32 */ if (end <= current)
/* */ {
/* */ try
/* */ {
/* 36 */ PooledStmt stmt = DBMgr.borrowSingleStmt(stmtId);
/* */
/* */
/* 39 */ stmt.setByte(3, type);
/* 40 */ stmt.executeUpdate();
/* 41 */ current = stmt.getInt(1);
/* 42 */ end = stmt.getInt(2);
/* 43 */ stmt.returnMe();
/* */ } catch (BtirException e) {
/* 45 */ current = (end = 0);
/* 46 */ log.error("can't get id for type=" + type);
/* 47 */ log.error(MiscUtil.traceInfo(e));
/* 48 */ return 0;
/* */ }
/* 50 */ if (end <= current)
/* 51 */ return 0;
/* */ }
/* 53 */ return current++;
/* */ }
/* */
/* */ public synchronized int getId(byte type, PooledStmt stmt) {
/* 57 */ if (end <= current) {
/* */ try {
/* 59 */ stmt.setByte(3, type);
/* 60 */ stmt.executeUpdate();
/* 61 */ current = stmt.getInt(1);
/* 62 */ end = stmt.getInt(2);
/* */ } catch (BtirException e) {
/* 64 */ current = (end = 0);
/* 65 */ return 0;
/* */ }
/* 67 */ if (end <= current)
/* 68 */ return 0;
/* */ }
/* 70 */ return current++;
/* */ }
/* */ }

上面这段代码主要是调用存储过程,对应配置的表的ID自增。。。

分布式数据库主键id生成策略的更多相关文章

  1. 数据库主键ID生成策略

    前言: 系统唯一ID是我们在设计一个系统的时候常常会遇见的问题,下面介绍一些常见的ID生成策略. Sequence ID UUID GUID COMB Snowflake 最开始的自增ID为了实现分库 ...

  2. 数据库分库分表(一)常见分布式主键ID生成策略

    主键生成策略 系统唯一ID是我们在设计一个系统的时候常常会遇见的问题,下面介绍一些常见的ID生成策略. Sequence ID UUID GUID COMB Snowflake 最开始的自增ID为了实 ...

  3. mybatis 针对SQL Server 的 主键id生成策略

    SQL Server中命令: select newId()  ,可以得到SQL server数据库原生的UUID值,因此我们可以将这条指令写到 Mybatis的主键生成策略配置selectKey中. ...

  4. Hibernate系列之ID生成策略

    一.概述 hibernate中使用两种方式实现主键生成策略,分别是XML生成id和注解方式(@GeneratedValue),下面逐一进行总结. 二.XML配置方法 这种方式是在XX.hbm.xml文 ...

  5. JPA ID生成策略(转---)

    尊重原创:http://tendyming.iteye.com/blog/2024985 JPA ID生成策略 @Table Table用来定义entity主表的name,catalog,schema ...

  6. 分库分表的 9种分布式主键ID 生成方案,挺全乎的

    <sharding-jdbc 分库分表的 4种分片策略> 中我们介绍了 sharding-jdbc 4种分片策略的使用场景,可以满足基础的分片功能开发,这篇我们来看看分库分表后,应该如何为 ...

  7. hibernate(四)ID生成策略

    一.ID生成策略配置 1.ID生成方式在xml中配置方式: <?xml version="1.0"?> <!DOCTYPE hibernate-mapping P ...

  8. 业务ID 生成策略

    业务ID 生成策略,从技术上说,基本要借助一个集中式的引擎来帮忙实现. 为了扩大业务ID生成策略的并发问题,还有更为技巧性的提升. 先来介绍普遍的分布式ID生成策略: 1. 利用DB的自增主键 这里又 ...

  9. Rhythmk 学习 Hibernate 03 - Hibernate 之 延时加载 以及 ID 生成策略

    Hibernate 加载数据 有get,跟Load 1.懒加载: 使用session.load(type,id)获取对象,并不读取数据库,只有在使用返回对象值才正真去查询数据库. @Test publ ...

随机推荐

  1. android onSaveInstance方法

    为什么需要用到Activity状态保存, 如何用 ? 1)我们希望当前的Activity中的信息不会因为Activity状态的改变,而丢失.比如横竖屏的切换,突然来了个电话. 2) 借助Activit ...

  2. cs108 04 oop design

    oop design 分为以下几个方面: - encapsulation and modularity(封装和模块化) - API/Client interface design(API 接口给调用类 ...

  3. Geometric deep learning on graphs and manifolds using mixture model CNNs

    Monti, Federico, et al. "Geometric deep learning on graphs and manifolds using mixture model CN ...

  4. tensorflow函数解析:Session.run和Tensor.eval的区别

    tensorflow函数解析:Session.run和Tensor.eval 翻译 2017年04月20日 15:05:50 标签: tensorflow / 机器学习 / 深度学习 / python ...

  5. Spring零散所得

    Spring容器中bean的id或name,都可以有多个,且第一个为标识符(Qualifier),其余皆为别名(Alias).所以都可以通过applicationContext.getBean(&qu ...

  6. C++ 类 & 对象

    C++ 类 & 对象C++ 在 C 语言的基础上增加了面向对象编程,C++ 支持面向对象程序设计.类是 C++ 的核心特性,通常被称为用户定义的类型. 类用于指定对象的形式,它包含了数据表示法 ...

  7. jquery中判断选择器,找没找到元素用$().size()==0

    jquery中判断选择器,找没找到元素用$().size()==0

  8. MathType中公式不对齐怎么办

    MathType是一款专门用来编辑数学公式的数学公式编辑器,利用它可以在文档中快速编辑公式,与文字完美结合,可以编辑出各种各样的数学符号与公式,省下你不少的时间. 一.对齐上标与下标 MathType ...

  9. Java中的各种加密算法

    Java中为我们提供了丰富的加密技术,可以基本的分为单向加密和非对称加密 1.单向加密算法 单向加密算法主要用来验证数据传输的过程中,是否被篡改过. BASE64 严格地说,属于编码格式,而非加密算法 ...

  10. [转]ASP.NET MVC 5 - 创建连接字符串(Connection String)并使用SQL Server LocalDB

    您创建的MovieDBContext类负责处理连接到数据库,并将Movie对象映射到数据库记录的任务中.你可能会问一个问题,如何指定它将连接到数据库? 实际上,确实没有指定要使用的数据库,Entity ...