2014-02-21 43 views

回答

2

“KEYS *”命令的内部行为是线性扫描主词典以收集所有键,并生成结果。过期的密钥被排除在外。下面是实现:

void keysCommand(redisClient *c) { 
    dictIterator *di; 
    dictEntry *de; 
    sds pattern = c->argv[1]->ptr; 
    int plen = sdslen(pattern), allkeys; 
    unsigned long numkeys = 0; 
    void *replylen = addDeferredMultiBulkLength(c); 

    di = dictGetSafeIterator(c->db->dict); 
    allkeys = (pattern[0] == '*' && pattern[1] == '\0'); 
    while((de = dictNext(di)) != NULL) { 
     sds key = dictGetKey(de); 
     robj *keyobj; 

     if (allkeys || stringmatchlen(pattern,plen,key,sdslen(key),0)) { 
      keyobj = createStringObject(key,sdslen(key)); 
      if (expireIfNeeded(c->db,keyobj) == 0) { 
       addReplyBulk(c,keyobj); 
       numkeys++; 
      } 
      decrRefCount(keyobj); 
     } 
    } 
    dictReleaseIterator(di); 
    setDeferredMultiBulkLength(c,replylen,numkeys); 
} 

虽然这种操作发生时,没有其他命令可以Redis的服务器上执行,事件循环正对KEYS命令的结果悬而未决。如果密钥数量很大(> 10K),客户端会注意到服务器不再有响应。

这是一个仅用于调试目的的命令。不要在应用程序中使用它。