1 基本场景
比如你有 N 个 cache 服务器(后面简称 cache ),那么如何将一个对象 object 映射到 N 个 cache 上呢,你很可能会采用类似下面的通用方法计算 object 的 hash 值,然后均匀的映射到到 N 个 cache ;

hash(object)%N

一切都运行正常,再考虑如下的两种情况;

1 一个 cache 服务器 m down 掉了(在实际应用中必须要考虑这种情况),这样所有映射到 cache m 的对象都会失效,怎么办,需要把 cache m 从 cache 中移除,这时候 cache 是 N-1 台,映射公式变成了 hash(object)%(N-1) ;

2 由于访问加重,需要添加 cache ,这时候 cache 是 N+1 台,映射公式变成了 hash(object)%(N+1) ;

1 和 2 意味着什么?这意味着突然之间几乎所有的 cache 都失效了。对于服务器而言,这是一场灾难,洪水般的访问都会直接冲向后台服务器;

再来考虑第三个问题,由于硬件能力越来越强,你可能想让后面添加的节点多做点活,显然上面的 hash 算法也做不到。

有什么方法可以改变这个状况呢,这就是 consistent hashing…

2 hash 算法和单调性
Hash 算法的一个衡量指标是单调性( Monotonicity ),定义如下:

单调性是指如果已经有一些内容通过哈希分派到了相应的缓冲中,又有新的缓冲加入到系统中。哈希的结果应能够保证原有已分配的内容可以被映射到新的缓冲中去,而不会被映射到旧的缓冲集合中的其他缓冲区。

容易看到,上面的简单 hash 算法 hash(object)%N 难以满足单调性要求。

3 consistent hashing 算法的原理
consistent hashing 是一种 hash 算法,简单的说,在移除 / 添加一个 cache 时,它能够尽可能小的改变已存在 key 映射关系,尽可能的满足单调性的要求。

下面就来按照 5 个步骤简单讲讲 consistent hashing 算法的基本原理。

3.1 环形hash 空间
考虑通常的 hash 算法都是将 value 映射到一个 32 为的 key 值,也即是 0~2^32-1 次方的数值空间;我们可以将这个空间想象成一个首( 0 )尾( 2^32-1 )相接的圆环,如下面图 1 所示的那样。

Read More →

一般把APP接口分为三类,普通接口,表单接口,会员接口;本文重点讨论会员接口
普通接口
一般为GET请求,比如获取新闻列表 GET http://Example.com/index.PHP?module=news&action=list,为了防止采集或者暴力查询,我们PC端一般做如下处理:
防止本站被它站file_get_contents,所以要识别user_agent,如果不是通过浏览器来访问的话直接不给看。
如果别人通过伪造user_agent来访问的话,就通过单位时间ip的访问量来控制抓取方,可以写一套算法,如果再一个ip在前后一分钟多于多少次访问量来处理。但是,会有一种情况,即某个小区或公司内都是使用某一个IP的外网的话,这样搞就会自寻死路,所以还要配合浏览器中的cookie来处理
总结: 请求头可以伪造,IP地址可以变更,cookie可以清空,基本上PC端是很难防这个问题的,比如淘宝,点评等大站的数据我也是经常去采的。

Read More →

很多时候我们都会用到referer地址,通过判断上一页是从哪里来的,我们可以了解很多信息,但是现在referer并不是那么可靠的数据了,因为我们可以伪造referer地址。这里分别介绍CURL、SOCKET、file_get_contents实现方法,详细代码如下:

CURL方式
$ch = curl_init();
curl_setopt ($ch, CURLOPT_URL, “http://www.shuzila.com”);
curl_setopt ($ch, CURLOPT_REFERER, “http://www.ailishuo.com/”);
curl_exec ($ch);
curl_close ($ch);

Read More →

如果你想用这个函数,请参考我的另外一篇文章。http://www.shangzh.com/21.html   PHP对二维数组的排序

原理是先排序之后,再根据某个键来删除,下面看代码

/**
* 根据某个键给二维数组去重,这个必须是排序的
* @param array $array
* @param string $keyid
* @return array
* @example array_unique_two($array,’id’);
*/
function array_unique_two($array, $key) {
if (is_array($array)) {
$first = reset($array); //获取第一个
array_shift($array); //删除第一个

$temp = $first[$key];//第一个值
if($array){
$res = [];
foreach($array as $val) {
if($val[$key] != $temp){
$res[] = $val;
$temp = $val[$key];
}
}
$data=[];
$data[] = $first;
$array = array_merge($data,(array)$res);
}else{
$array = $first;
}

}
return $array;
}

安装memcached

wget http://memcached.org/files/memcached-1.4.24.tar.gz
tar -zxvf memcached-1.4.24.tar.gz
cd memcached-1.4.24
./configure && make && make test && sudo make install

memcached启动
/usr/local/bin/memcached -d -m 50 -u root -p 11211 -c 1024 -P /tmp/memcached.pid

memcached终止
kill `cat /tmp/memcached.pid`

http://www.cppblog.com/kefeng/archive/2010/10/11/129422.html

安装 memcached扩展

wget https://sourceforge.net/projects/levent/files/libevent/libevent-2.0/libevent-2.0.22-stable.tar.gz

tar -zxvf libevent-2.0.22-stable.tar.gz
cd libevent-2.0.22-stable
./configure
make
make install

wget https://launchpad.net/libmemcached/1.0/1.0.18/+download/libmemcached-1.0.18.tar.gz
tar -zxvf libmemcached-1.0.18.tar.gz
cd libmemcached-1.0.18
./configure
make
make install

libmemcached 默认安装在/usr/local/,头文件安装在/usr/local/include/libmemcachde/,动态库默认安装在/usr/local/lib/下。

wget pecl.php.net/get/memcached-2.2.0.tgz
tar -zxvf memcached-2.2.0.tgz
cd memcached-2.2.0
whereis phpize
/usr/bin/phpize && ./configure –with-php-config=/usr/local/php/bin/php-config –enable-memcache=/usr/local/include/libmemcached –disable-memcached-sasl && make && make install

[memcache]
extension_dir=/usr/local/php/lib/php/extensions/no-debug-non-zts-20100525/
extension=”memcache.so”