memcached客户端
/**
* Created by pc on 2018/6/22.
*/
import Vo.UserModel;
import net.rubyeye.xmemcached.*;
import net.rubyeye.xmemcached.exception.MemcachedException;
import net.rubyeye.xmemcached.utils.AddrUtil;
import java.io.IOException;
import java.util.concurrent.TimeoutException;
/**
* describe:
*
* @author xxx
* @date4 {YEAR}/06/22
*/
public class ShowApi {
//新增set,add
private static void showAdd(UserModel um) throws IOException, InterruptedException, MemcachedException, TimeoutException {
MemcachedClientBuilder builder = new XMemcachedClientBuilder(AddrUtil.getAddresses("101.200.63.29:2222"));
MemcachedClient memcachedClient = builder.build();
memcachedClient.set("k6",0,um);
//修改replace,append,prepend
memcachedClient.replace("k6",0,um);
//删除delete
//查询gets
GetsResponse<UserModel> gets = memcachedClient.gets("k6");
//数值操作decr/incr
memcachedClient.incr("k5", 5, 10);//如果key不存在则第三个参数为初始值,存在则递增或递减,不能减除负数
//1. 检查更新cas结合gets
GetsResponse<UserModel> get = gets;
//2. 先获取版本号
long cas = get.getCas();
//3. 进行更新
memcachedClient.cas("k6",0,um,cas);
//更新数据过期时间
memcachedClient.touch("k6",3600);
//操作Xmemcached操作的cas
memcachedClient.cas("k6", new CASOperation<String>() {
//重试次数
public int getMaxTries() {
return 1;
}
public String getNewValue(long cas, String currentValue) {
return currentValue;
}
});
//计数器
Counter counter = new Counter(memcachedClient,"k6",12);
//加入命名空间后,key的前缀加上命名空间名
}
public static UserModel get(String key) throws InterruptedException, MemcachedException, TimeoutException, IOException {
MemcachedClientBuilder builder = new XMemcachedClientBuilder(AddrUtil.getAddresses("101.200.63.29:2222"));
MemcachedClient memcachedClient = builder.build();
return memcachedClient.get(key);
}
public static void main(String[] args) throws InterruptedException, TimeoutException, MemcachedException, IOException {
UserModel userModel = new UserModel(1,"22",3);
showAdd(userModel);
System.out.println(get("k6"));
}
}
memcached余数哈希算法
1. 将传入的key转换为hash值
2. 获取服务器数量列表
3. Hash值%服务器数量
4. 通过余数来选择具体存放或查询的服务器
memcached一致性哈希算法
1. 将服务器列表+虚拟节点分布在0-2的32次方的一个圆上
2. 将传入的key转换为Hash值
3. Hash值%服务器数量
4. 通过余数来选择具体存放或查询的服务器
5. 如果余数命中虚拟节点,则会顺时针寻找真实Memcached服务
两段Hash:1. 客户端通过Hash算法寻找存储查询的节点
2. 进入Memcached以后,通过Hash算法,寻找具体的chunk
![](https://i-blog.csdnimg.cn/blog_migrate/dade80e2bb82afecbd41c0a8c5e954d9.png)
libevent:
1. 解压缩
2. ./configurue=/usr/local/install/libevent(安装路径)
3. make & make install
memcached雷同
1.
2. ./configure=/usr/local/install/memcached --with-libevent=/usr/local/install/libevent
memcached
set k1,0,0,2(key,flag,过期时间,length[bytes]) :无论什么情况下都可以插入
add k2,0,0,2 :只有当key不存在时才可以插入
replace:当键存在时,更换值
append:已有结果添加数据(key,flags,exTime,追加的长度)
prepend:已有数据前
cas:检查更新(key,flags,exTime,length,version->value)(1 .输入待修改的数据+版本号2. memcached检测版本号是否正确3. 如果正确则修改数据)
delete:删除数据(并不会真正删除数据,而是将数据打一个删除标记)
incr/decr:增加数值/减少数值
内存分配
1. slab
2. page
3.chunk(真正存储数据)
自增长因子1.25,同slab同chunk不同slab不同chunk
存储样式 slabclass: 80=slab1,slab2,slab3 100=slab4 125=slab5,slab6
找不到chunk出发LRU流程(最近最少使用)