python操作memcached的常用方法
1.创建memcache对象
#!/usr/bin/env python
# -*-coding:utf-8-*-
import memcache
mc = memcache.Client(["192.168.31.10:11211"], debug=True) #debug为调试参数
mc.set("foo", "123")
print mc.get("foo")
2.python使用memcache集群
python-memcached模块原生支持集群操作,其原理是在内存维护一个主机列表,且集群中主机的权重值和主机在列表中出现的次数成正比.
集群memcache服务器,python 对数据保存在那台服务器位置的算法是如下
如果用户根据如果要在内存中创建一个键值对(如:k1 = "v1"),那么要执行一下步骤:
- 根据算法将 k1 转换成一个数字
- 将数字和主机列表长度求余数,得到一个值 N( 0 <= N < 列表长度 )
- 在主机列表中根据 第2步得到的值为索引获取主机,例如:host_list[N]
- 连接 将第3步中获取的主机,将 k1 = "v1" 放置在该服务器的内存中.
集群设置方法:
#!/usr/bin/env python
# -*-coding:utf-8-*-
import memcache
mc = memcache.Client([("192.168.31.10:11211", 1), ("192.168.31.7:11211", 3), ("192.168.31.7:11211", 1)], debug=True)
mc.set("foo", "abc")
print mc.get("foo")
注:集群设置中,服务器的列表地址元素是元组了(主机地址, 权重)
3.增加数据add
对已经存在的key使用add会报异常.set方法不会.这点也是他们2的区别
#!/usr/bin/env python
# -*-coding:utf-8-*-
import memcache
mc = memcache.Client([("192.168.31.10:11211", 1), ("192.168.31.7:11211", 3), ("192.168.31.7:11211", 1)], debug=True)
mc.set("foo", "abc")
print mc.get("foo")
mc.set("foo", "456")
print mc.get("foo")
mc.add("foo", "abc")
4.修改数据replace
replace 修改某个key的值,如果key不存在,则异常.
mc.replace("k1", "v2")
print mc.get("k1")
上述代码中,k1的键是不存在的.执行replace会报如下异常
MemCached: while expecting 'STORED', got unexpected response 'NOT_STORED'
Non
5.设置键值对set和set _multi
set 设置一个键值对,如果key不存在,则创建,如果key存在,则修改.
set_multi 设置多个键值对,如果key不存在,则创建,如果key存在,则修改.
mc.set("k1", "v1")
print mc.get("k1")
mc.set_multi({"k2":"v2", "k3":"v3"})
print mc.get("k3")
执行结果
v1
v3
6.delete 和 delete_multi
delete 在Memcached中删除指定的一个键值对
delete_multi 在Memcached中删除指定的多个键值对.参数是列表
mc.set("k1", "v1")
print mc.get("k1")
mc.delete("k1")
print mc.get("k1")
mc.set_multi({"k2":"v2", "k3":"v3"})
print mc.get("k3")
mc.delete_multi(["k3"])
print mc.get("k3")
执行结果
v1
None
v3
None
7.在值的前面或者后面增加值append 和 prepend
append 修改指定key的值,在该值 后面 追加内容
prepend 修改指定key的值,在该值 前面 插入内容
mc.set("k1", "abc")
print mc.get("k1")
mc.prepend("k1", "pre--")
print mc.get("k1")
mc.append("k1", "--app")
print mc.get("k1")
执行结果
abc
pre--abc
pre--abc--app
8.自增或者自减值decr 和 incr
incr 自增,将Memcached中的某一个值增加 N ( N默认为1 )
decr 自减,将Memcached中的某一个值减少 N ( N默认为1 )
mc.set("k1", "10")
print mc.get("k1")
mc.incr("k1")
print mc.get("k1")
mc.incr("k1", 10)
print mc.get("k1")
mc.decr(("k1"))
print mc.get("k1")
执行结果
10
11
21
20
9.避免脏数据产生的获取和设置方法
如商城商品剩余个数,假设改值保存在memcache中,product_count = 900
A用户刷新页面从memcache中读取到product_count = 900
B用户刷新页面从memcache中读取到product_count = 900
如果A、B用户均购买商品
A用户修改商品剩余个数 product_count=899
B用户修改商品剩余个数 product_count=899
如此一来缓存内的数据便不在正确,两个用户购买商品后,商品剩余还是 899
如果使用python的set和get来操作以上过程,那么程序就会如上述所示情况!
如果想要避免此情况的发生,只要使用 gets 和 cas 即可,如:
import memcache
import time
mc = memcache.Client([("192.168.31.10:11211", 1), ("192.168.31.7:11211", 3), ("192.168.31.7:11211", 1)], debug=True, cache_cas=True)
print mc.gets("foo")
print mc.cas_ids
time.sleep(10)
mc.cas("foo", '999')
print mc.cas_ids
2个这客户端同时修改同一份数据时.会报如下错误
999
{'foo': 43}
MemCached: while expecting 'STORED', got unexpected response 'EXISTS'
{'foo': 43}
注:cache_cas=True 一定要打开.不然无法使用上面的特性