请选择 进入手机版 | 继续访问电脑版

Redis中国用户组(CRUG)论坛

 找回密码
 立即注册

QQ登录

只需一步,快速开始

扫一扫,访问微社区

搜索
热搜: 活动 交友 discuz
查看: 7414|回复: 0

redis实现简单的条件查询功能

[复制链接]
  • TA的每日心情
    开心
    2016-10-27 12:14
  • 签到天数: 89 天

    [LV.6]常住居民II

    357

    主题

    456

    帖子

    3594

    积分

    管理员

    Rank: 9Rank: 9Rank: 9

    积分
    3594

    最佳新人活跃会员宣传达人突出贡献优秀版主荣誉管理论坛元老

    发表于 2016-3-1 11:16:22 | 显示全部楼层 |阅读模式

    今天在学习redis的时候,遇到了一个让我很纠结的问题。在sql语句中,条件查询是很简单实现的,比如:

    1. select * from books where id = 1
    复制代码


    这条SQL语句就能够很简单的挑选出来表books里面id等于1的书本的全部信息。但是,redis是非关系型数据库,并不支持这种通过“键值=value”查询数据的方式,那我们究竟该怎样实现类似的条件查询呢?

    在登陆注册场景中,我们这样实现用户登陆时候的用户名判断。我们先假定用户信息只有用户名和密码。

    注册:



    1. exports.handle_regist = function(username,password){
    2.   client.incr('uid');
    3.   client.get('uid',function(err,uid){
    4.   //建立索引集合,username--id
    5.     client.set('username:'+username,uid);
    6.     client.hmset("user:"+uid,'username',username,'password',password,function(err){
    7.       if(err){
    8.         return 0;
    9.       }
    10.       else{
    11.         return 1;
    12.       }
    13.     });
    14.   });
    15. };

    复制代码


    这段代码中,我们实现的是存储用户的用户名和密码的操作。

    1. client.incr('uid');
    复制代码

    创建 键名为uid的字符串类型键值对,每次有用户注册的数据传入时候,我们都会将uid自增1。这样,其实我们就能够知道下一位用户注册时候我们应该给他分配的uid是多少了。那为什么要分配uid呢?是为了在后面建立hash类型的键值对时候需要用到,一会再说。

    1. client.<b>get</b>(<font color="#dd1144">'uid'</font>,function(err,uid){...}
    复制代码


    这行代码是干嘛的呢?很明显,我们用来挑选出字符串类型的并且key=uid的value,得到value之后,实际上我们就能够为注册的用户分配唯一的ID.

    1. client.set('username:'+username,uid);
    复制代码


    这行代码很关键,我们在这里设置了一个“username:zhou=>1”类型的键值对索引。(‘zhou’是传过来的用户名,1是刚才得到的uid)。那么这个键值对又是干嘛的?

    这个就是实现条件索引的关键了,我们为用户名和用户id建立联系,当需要挑选出用户名为zhou的用户的密码的时候,我们首先通过这个键值对索引,找到该用户的uid,再通过这个uid得到用户名密码。这样,思路就清晰了。

    1. client.hmset("user:"+uid,'username',username,'password',password,function(err){...}
    复制代码


    这行代码中,我们才是真正的储存用户名和密码。可以看到,我们建立了“user:1=>{username='zhou',password='123'}”形式的键值对,其中user:uid是键名,username,password是键值中的字段,用户信息是键值中字段值。这样我们就能实现用户信息的储存了。

    登陆功能:




    1. exports.handle_login = function(username,password,callback){
    2.   client.get('username:'+username,function(err,uid){
    3.     if(err){
    4.       return callback(err);
    5.     }
    6.     else{
    7.       client.hget('user:'+uid,'password',function(err,pass){
    8.         if(err){
    9.           var msg = 0;
    10.           return callback(msg);
    11.         }
    12.         if(password == pass){
    13.           var msg = 1;
    14.           return callback(msg);
    15.         }
    16.         else{
    17.           var msg = 2;
    18.           return callback(msg);
    19.         }
    20.       });
    21.     }
    22.   });
    23. };
    复制代码
    1. client.get('username:'+username,function(err,uid){
    复制代码


    我们首先通过传过来的username,在键值对“username:zhou=>uid”中寻找uid,如果没有该uid,说明没有注册,返回一个状态码;

    如果找到uid,说明该用户名已经注册过,接着判断password。


    1. client.hget('user:'+uid,'password',function(err,pass){
    复制代码

    通过之前得到的uid查询用户信息键值对,得到password,判断用户输入的密码是否匹配,这样就能完成判断。

    总结:通过以上过程不难发现,redis实现条件查询其实就是需要我们自己建立id与其他属性的联系集。比如在关系型数据库里面,建立一个汽车表car:car_id,color,price.location.当我们需要查询color等于white的所有汽车信息的时候,我们首先需要建立一个car_id和color之间的联系集,color:color_value=>uid,通过匹配得到uid再去查找汽车信息。这个方法看起来有点麻烦,但还是不知道有什么方法能替代(lua脚本是啥?)

    本文转自:http://www.tuicool.com/articles/2YVRVby






    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    阿里云
    阿里云

    Archiver|手机版|小黑屋|Redis中国用户组 ( 京ICP备15003959号

    GMT+8, 2017-2-20 04:59 , Processed in 0.105416 second(s), 28 queries .

    Powered by Discuz! X3.2

    © 2001-2013 Comsenz Inc.

    快速回复 返回顶部 返回列表