数据库水平分表算法实现

数据库水平分表算法实现介绍如下:

一:实现思想

      以MurmurHash算法为基础,在MurmurHash算法进行必要改造,本次主要进行64分表,即分为64个主表,实现思想简介如下:

      1、MurmurHash生成hashcode      ---详细可看代码

      2、hashcode取模64生成分表下表,---详细可看代码

      3、分表的下表拼接                          ---详细可看代码

具体细节可参考code,如下;

二:code实现

/**
 * 描述:分表生成及常用方法统一提供
 * @author Aaron
 * @version 1.0
 * @param args
 */
public class HashTableIndex
{
     private static  StringBuffer stringBuffer = null;
     static {
         if (null == stringBuffer) {
             stringBuffer = new StringBuffer();
         }
     }


    public static  long hash64A(ByteBuffer buf, int seed)
    {
        ByteOrder byteOrder = buf.order();
        buf.order(ByteOrder.LITTLE_ENDIAN);

        long m = 0xc6a4a7935bd1e995L;
        int r = 47;

        long h = seed ^ (buf.remaining() * m);

        long k;
        while (buf.remaining() >= 8)
        {
            k = buf.getLong();

            k *= m;
            k ^= k >>> r;
            k *= m;

            h ^= k;
            h *= m;
        }

        if (buf.remaining() > 0)
        {
            ByteBuffer finish = ByteBuffer.allocate(8).order(ByteOrder.LITTLE_ENDIAN);
            finish.put(buf).rewind();
            h ^= finish.getLong();
            h *= m;
        }

        h ^= h >>> r;
        h *= m;
        h ^= h >>> r;

        buf.order(byteOrder);
        return h;
    }

    /**
     * @author Aaron 描述:hash值生成
     * @param key
     * @return
     */
    public static long hash(byte[] key)
    {
        return hash64A(ByteBuffer.wrap(key), 0x1234ABCD);
    }

    /**
     * @author Aaron
     * 描述:64个分表hash下表生成
     */
    public static long getTableBelow(String userId)
    {
        return Math.abs(hash(SafeEncoder.encode(userId)) % 64);
    }
    
    
    /**
     * 描述:根据入参tableName、tableIndex生成分表
     * @author Aaron
     * @version 1.0
     * @param args
     */
    public static String getTableName(String tableName,long tableIndex) {
        //枚举匹配
        for(TableName tname :TableName.values()) {
            if(tname.toString().equals(tableName)) {
                stringBuffer = stringBuffer.delete(0, stringBuffer.length()).append(tableName).append("_").append(tableIndex);
            }
        }      
        return stringBuffer.toString();
    }
    
    /**
     * 描述:根据入参tableName、userId生成分表
     * @author Aaron
     * @param args
     */    
    public static String getTableName(String tableName,String userId) {
        //枚举匹配
        //stringBuffer=null;
        for(TableName tname :TableName.values()) {
            if(tname.toString().equals(tableName)) {
                stringBuffer = stringBuffer.delete(0, stringBuffer.length()).append(tname).append("_").append(getTableBelow(userId));
            }
        }      
        return stringBuffer.toString();
    }
    
    /**
     * 描述:根据入参tableName、userId查询分表
     * @author Aaron
     * @param args
     */
    public static String selectChildTableName(String tableName,String userId) {
        //枚举匹配
        for(TableName tname :TableName.values()) {
            if(tname.toString().equals(tableName)) {
                stringBuffer = stringBuffer.delete(0, stringBuffer.length()).append(tname).append("_").append(getTableBelow(userId));
            }
        }      
        return stringBuffer.toString();
    }

    // 测试
    public static void main(String[] args)
    {
        //System.out.println(getTableBelow("39666665"));
        System.out.println("-----------"+getTableName("user",getTableBelow("565")));
        System.out.println("-----------"+getTableName("user","565"));
    }

}


有问题可评论区讨论,欢迎大家指出不足,便于共同进步!!!!

作者:Aaron 
邮箱:[email protected]
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。如果觉得还有帮助的话,可以点一下右下角的 【推荐】


猜你喜欢

转载自blog.csdn.net/weixin_37186559/article/details/80178504
今日推荐