Redis内部实现(独立功能实现)

来源:互联网 发布:美国2016年7月非农数据 编辑:程序博客网 时间:2024/06/05 11:43

1. Redis内部实现

1.1. 独立功能实现

1.1.1. 发布和订阅

1)启动redis-cli,订阅new.*消息

redis 127.0.0.1:6379> psubscribe news.*

Reading messages... (press Ctrl-C to quit)

1) "psubscribe"

2) "news.*"

3) (integer) 1

2)启动另一个redis-cli用来发布两条消息:

redis 127.0.0.1:6379> publish news.share "share a link http://www.google.com"

(integer) 2

redis 127.0.0.1:6379> publish news.blog "I post a blog"

(integer) 2

3)此时之前订阅的client会打印:

1) "pmessage"

2) "news.*"

3) "news.share"

4) "share a link http://www.google.com"

1) "pmessage"

2) "news.*"

3) "news.blog"

4) "I post a blog" 

1.1.2. 事务:

将多个命令打包,一次性执行多条命令。

127.0.0.1:6379> multi     //开始对下面命令进行打包

OK

127.0.0.1:6379> SET “name” “Practical Common Lisp”

QUEUED

127.0.0.1:6379> GET “name” 

QUEUED

127.0.0.1:6379> SET “author” “Peter Seibel”

QUEUED

127.0.0.1:6379> GET “author” 

QUEUED

127.0.0.1:6379> EXEC    //执行命令包

1)OK

2) “Practical Common Lisp”

3)OK

4)“Peter Seibel”

Watch的乐观锁的作用:

127.0.0.1:6379> watch “name”   //watch下的name在事务将被拒绝执行

 

 

1.1.3. Lua脚本

通过redis.call('hexists', KEYS[3], KEYS[4])调用代替,redisCommandcontextformat),使更灵活。

抢红包案例:http://blog.csdn.net/hengyunabc/article/details/19433779

/*- 函数:尝试获得红包,如果成功,则返回json字符串,如果不成功,则返回空  

 *-- 参数:红包队列名, 已消费的队列名,去重的Map名,用户ID  

 *-- 返回值:nil 或者 json字符串,包含用户IDuserId,红包IDid,红包金额:money  

*/

 //-- 如果用户已抢过红包,则返回nil  

 if redis.call('hexists', KEYS[3], KEYS[4]) ~= 0 then  

     return nil  

else  

//-- 先取出一个小红包  

    local hongBao = redis.call('rpop', KEYS[1]);  

    if hongBao then  

        local x = cjson.decode(hongBao);  

        //-- 加入用户ID信息  

         x['userId'] = KEYS[4];  

         local re = cjson.encode(x);  

        //-- 把用户ID放到去重的set  

          redis.call('hset', KEYS[3], KEYS[4], KEYS[4]);  

         // -- 把红包放到已消费队列里  

         redis.call('lpush', KEYS[2], re);  

         return re;  

     end  

 end  

 return nil   

1.1.4. 排序

对象:setscoresetlist这三种。

1SORT <key> ASC升序排序,同SORT <key>也是升序

2SORT <key> DESC降序排序

3SORT <key> ALPHA可对字符串值进行排序,否则(1)(2)只能是数值.

4SORT <key> BY *-price

SORT <key> BY *-price

1)”banana”

2)”cherry”

3)”apple”

依据“元素+price”的权重键值做来排序,如

SADD fruite apple” “banana” “cherry

MSET apple-price 8 banana-price 5.5 cherry-price 7

SORT fruits BY *-price执行过程:

(a)    fruits元素拼接-price,组成如apple-price作为权重键,查的对应权重键值8.

(b)    根据每个元素的权重键值作为排序依据

 5      SORT <key> BY *-id ALPHA可对字符串值作为权重值进行排序,如下依据“id-8”,“id-5.5”,“id-7”字符串值排序。

SADD fruite apple” “banana” “cherry

MSET apple-id id-8 banana-id id-5.5 cherry-id id-7

6      SORT <key> LIMIT <offset><count>排序结果显示数量控制

7 127.0.0.1:6379> SORT studentALPHA 

127.0.0.1:6379> SORT studentALPHA 
1) "jack" 
2) "peter" 
3) "tom" 
127.0.0.1:6379> SET peter-name "Peterwhite" 
OK 
127.0.0.1:6379> set jack-name "JackSnow" 
OK 
127.0.0.1:6379> set tom-name "TomSmith" 
OK 
127.0.0.1:6379> SORT student ALPHA GET *-name 
1) "Jack Snow" 
2) "Peter white" 
3) "Tom Smith" 

依据“元素+name”作为程序返回键,并向客户端返回对应键值。

 GET可以是多个,如:

127.0.0.1:6379> SET peter-birth 1995-6-7 
OK 
127.0.0.1:6379> SET tom-birth 1995-8-7 
OK 
127.0.0.1:6379> SET jack-birth 1995-9-7 
OK 
127.0.0.1:6379> SORT student ALPHA GET *-name GET*-birth 
1) "Jack Snow" 
2) "1995-9-7" 
3) "Peter white" 
4) "1995-6-7" 
5) "Tom Smith" 
6) "1995-8-7" 

8      SORT <key> ALPHA STORE<key> STORE参数可以用于将排序结果保存为另一个key

   127.0.0.1:6379> SORT students ALPHA STORE sorted_students 

 

1.1.5. 二进制

可存二进制数值,并支持& ,|等位运算。 

1.1.6. 慢查询日志

保存内存链表中,通过命令查询 

127.0.0.1:6379> CONFIG SET slowlog-log-slower-then 0 //记录执行时间超过多少微秒的命令,0表示所有命令都记录

127.0.0.1:6379> CONFIG SET slowlog-max-len 5     //最多保存多少条慢查询日志

127.0.0.1:6379> SLOWLOG GET 

1.1.7. 监视器

127.0.0.1:6379> MONITOR

通过设置监视模式,客户端可以查看每个客户端发向服务器侧的命令

0 0