分表,分库算法

摘要:
主机分布式主机选择算法1:使用crc32哈希˂?这很简单。因为哈希算法直接映射数组下标,所以搜索算法的时间复杂度为O。因此,拥有一个好的哈希码算法尤为重要,这样任何给定的元素都可以统一存储在哈希表的每个桶中。下面给出了一个非常经典的通用哈希算法,研究人员对其进行了统计分析。

经典案例:

1:在memcache中分key存储。主机分布式选择主机的算法

一:利用crc32散列

    <?php
    //范围:00-63
    function crc_hash(&$keyword,$n=64)
    {
    $hash = crc32($keyword) >> 16 & 0xffff;
    return sprintf("%02s",$hash % $n);
    }
    ?>

 二:当用户数量太多(如达到千万级别),数量量太大时,我们会根据用户名username使用hash算法得出0-N的一个数值,将用户信息分散存储到N个表中,如增加用户信息示例代码如下:

    <?php

    function getHash(&$keyword,$n)
    {
    $hash = crc32($keyword) >> 16 & 0xffff;
    return sprintf("%02s",$hash % $n);
    }

    $table = 'userinfo_'.getHash($username,100);

    $sql = "insert into {$table} values(....)";

    $db = new models($table);//封装的数据库操作类
    $db->MyInsert($sql);

    ?>

 三:

hash算法一般是利用数组实现的,步骤如下:
存元素时:
1.把要存储的元素(value)计算一个hashcode(称为散列),这个就是key。
2.把元素存储到以hashcode为下标的数组中。
3.若此数组下标已经有元素,则使用链表的方式把元素连接起来。

获得元素时:
1.元素(value)计算hashcode。
2.hash表中按hashcode(key)取得元素。
3.若一个key中对应多个元素,则还需匹配是哪个元素。

就这么简单,hash算法由于直接映射数组下标,所以查找算法的时间复杂度来说是O(1)的。不过若计算hashcode的算法不是很好的话,可能 造成一个桶(数组中的一个位置)内有多个元素,而有些桶内一个元素都没有。这样在存、取元素时都需要在桶内进行查找操作,而且造成空间的浪费。所以一个好的hashcode的算法使得任意给定的元素能够均匀地存储在hash表中的每个桶内,显得尤为重要。以下给出一个非常经典的通用散列算法,经过研究人员统计分析过散列程度的。

    unsigned long hashcode(const unsigned char *name)
    {
    unsigned long h=0,g;
    while(*name)
    {
    h=(h<<4) + *name++;
    if(g=h & 0xF0000000)
    h^=g>>24;
    h &=~g;
    }
    return h;
    }

除非你对这个通用散列算法有特殊需求,导致无法满足需要,否则应该使用这个函数。

hash算法确实应用得非常广泛,因为其查找的速度是O(1)的。比如:如今数据的海量存取和高并发访问的需求,造成关系数据库逐渐退出舞台。DB中使用B+树索引提供范围查询,hash(key-value)索引实现点查询。

例子:

在开发中,整型的数值可以通过取模(mod)来进行分表,但是,对于帐号这种字符串类型,却不能实现。怎么办呢,我们可以通过CRC32这个函数来分表,函数如下:

function account_hash($account,$tail=4,$mod=1)
{
$crc32=sprintf("%u",crc32($account));//使用%u解决32位下出现负数的问题
return fmod(substr(strval($crc32),-$tail,$tail),$mod); //取模计算数值
}



使用这个函数,可以灵活定义分表的离散程度和分表数量

参考:http://www.dewen.io/q/405/%E6%B1%82mysql+%E5%88%86%E8%A1%A8%E7%9A%84%E6%84%8F%E4%B9%89

  1. <?php
  2. //范围:00-63
  3. function crc_hash(&$keyword,$n=64)
  4. {
  5. $hash = crc32($keyword)>>16&0xffff;
  6. return sprintf("%02s",$hash % $n);
  7. }
  8. ?>

免责声明:文章转载自《分表,分库算法》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇ASP.NET MVC5开发记录WinForm中使用DXperience控件中XtraForm,如何实现换肤下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

nginx upstream模块

upstream模块 upstream模块 (100%) nginx模块一般被分成三大类:handler、filter和upstream。前面的章节中,读者已经了解了handler、filter。 利用这两类模块,可以使nginx轻松完成任何单机工作。而本章介绍的upstream,将使nginx将跨越单机的限制,完成网络数据的接收、处理和转 发。 数据转...

HashMap在并发下可能出现的问题分析

我们都知道,HashMap在并发环境下使用可能出现问题,但是具体表现,以及为什么出现并发问题,可能并不是所有人都了解,这篇文章记录一下HashMap在多线程环境下可能出现的问题以及如何避免。 在分析HashMap的并发问题前,先简单了解HashMap的put和get基本操作是如何实现的。 1.HashMap的put和get操作 大家知道HashMap内部实...

Linux-c glib库hash表GHashTable介绍

  百度云glib  链接:https://pan.baidu.com/s/1W9qdlMKWRKIFykenTVuWNQ 密码:ol6y hash表是一种提供key-value访问的数据结构,通过指定的key值可以快速的访问到与它相关联的value值。hash表的一种典型用法就是字典,通过单词的首字母能够快速的找到单词。关于hash表的详细介绍请查阅数据...

PHP 之sha256 sha512封装

PHP 之sha256 sha512封装/* PHP sha256 sha512目前(PHP 7.1)没有内置的函数来计算,sha1() sha1_file() md5() md5_file()分别可以用来计算字符串和文件的sha1散列值和md5散列值,当前最新版本PHP 7.1 sha256() sha256_file() sha512() sha512...

使用Python操作Redis详解

之前的五天,过了个愉快的周末,然后将公司AbaseDump的调度部分代码看懂并且在此之上完成了OnlyDump的功能代码,代码不可以公开,今天完工,明天测试,晚上来总结一下这几天学到的一点应用。 使用Python操作Redis详解 ---------------------------------------------------------------...

六.HashMap HashTable HashSet区别剖析总结

 HashMap、HashSet、HashTable之间的区别是Java程序员的一个常见面试题目,在此仅以此博客记录,并深入源代码进行分析: 在分析之前,先将其区别列于下面: 1、HashSet底层采用的是HashMap进行实现的,但是没有key-value,只有HashMap的key set的视图,HashSet不容许重复的对象 Hashtable是基...