Redis分布式缓存学习总结4(set数据类型)

1.简介

Redis 的 Set 是 string 类型的无序集合。

集合是通过哈希表实现的,所以添加,删除,查找的复杂度都是 O(1)。

集合中最大的成员数为 232- 1(4294967295, 每个集合可存储40多亿个成员)。

Redis zset 和 set 一样也是string类型元素的集合,且不允许重复的成员。

2.使用场景

集合主要应用在一些需要求交集、并集、补集这样的场景,比如我们需要求共同好友、共同兴趣爱好、共同关注的微博,限制同一个账号多处登录系统等场景。

3.set数据结构示意图

set类型在存储数据时,是以key-List<value>格式存储的,如下图所示:

Redis分布式缓存学习总结4(set数据类型)

 例如,一个用户tom,他的兴趣有编程,音乐,运动,就可以用set表示:

 Redis分布式缓存学习总结4(set数据类型)

 

如下是对set封装后的api方法,RedisSetService.cs,代码如下: 

using MyRedis.Redis.Interface;
using System.Collections.Generic;

namespace MyRedis.Redis.Service
{
    public class RedisSetService : RedisBase
    {

        #region 添加

        /// <summary>
        /// key集合中添加value
        /// </summary>
        /// <param name="key"></param>
        /// <param name="value"></param>
        public void AddItemToSet(string key, string value)
        {
            base.iClient.AddItemToSet(key, value);
        }


        /// <summary>
        /// key集合中添加list集合
        /// </summary>
        /// <param name="key"></param>
        /// <param name="list"></param>
        public void AddRangeToSet(string key, List<string> list)
        {
            base.iClient.AddRangeToSet(key, list);
        }

        #endregion


        #region 获取

        /// <summary>
        /// 随机获取key集合中的一个值
        /// </summary>
        /// <param name="key"></param>
        /// <returns></returns>
        public string GetRandomItemFromSet(string key)
        {
            return base.iClient.GetRandomItemFromSet(key);
        }

        /// <summary>
        /// 获取key集合值的数量
        /// </summary>
        /// <param name="key"></param>
        /// <returns></returns>
        public long GetSetCount(string key)
        {
            return base.iClient.GetSetCount(key);
        }

        /// <summary>
        /// 获取所有key集合的值
        /// </summary>
        /// <param name="key"></param>
        /// <returns></returns>
        public HashSet<string> GetAllItemsFromSet(string key)
        {
            return base.iClient.GetAllItemsFromSet(key);
        }

        #endregion


        #region 删除

        /// <summary>
        /// 随机删除key集合中的一个值
        /// </summary>
        /// <param name="key"></param>
        /// <returns></returns>
        public string PopItemFromSet(string key)
        {
            return base.iClient.PopItemFromSet(key);
        }

        /// <summary>
        /// 删除key集合中的value
        /// </summary>
        /// <param name="key"></param>
        /// <returns></returns>
        public void RemoveItemFromSet(string key, string value)
        {
            base.iClient.RemoveItemFromSet(key, value);
        }


        #endregion


        #region 其它

        /// <summary>
        /// 从fromkey集合中移除值为value的值,并把value添加到tokey集合中
        /// </summary>
        /// <param name="fromkey"></param>
        /// <param name="tokey"></param>
        /// <param name="value"></param>
        public void MoveBetweenSets(string fromkey, string tokey, string value)
        {
            base.iClient.MoveBetweenSets(fromkey, tokey, value);
        }


        /// <summary>
        /// 返回keys多个集合中的并集
        /// </summary>
        /// <param name="keys"></param>
        /// <returns></returns>
        public HashSet<string> GetUnionFromSets(params string[] keys)
        {
            return base.iClient.GetUnionFromSets(keys);
        }


        /// <summary>
        /// 返回keys多个集合中的交集
        /// </summary>
        /// <param name="keys"></param>
        /// <returns></returns>
        public HashSet<string> GetIntersectFromSets(params string[] keys)
        {
            return base.iClient.GetIntersectFromSets(keys);
        }


        /// <summary>
        /// 返回keys多个集合中的差集
        /// </summary>
        /// <param name="fromKey">原集合</param>
        /// <param name="keys">其它集合</param>
        /// <returns>出现在原集合,但不包括在其他集合</returns>
        public HashSet<string> GetDifferencesFromSet(string fromKey, params string[] keys)
        {
            return base.iClient.GetDifferencesFromSet(fromKey, keys);
        }


        /// <summary>
        /// keys多个集合中的并集,放入newkey集合中
        /// </summary>
        /// <param name="newkey"></param>
        /// <param name="keys"></param>
        public void StoreUnionFromSets(string newkey, string[] keys)
        {
            base.iClient.StoreUnionFromSets(newkey, keys);
        }


        /// <summary>
        /// 把fromkey集合中的数据与keys集合中的数据进行比对,fromkey集合中不存在keys集合中,则把这些不存在的数据放入newkey
        /// </summary>
        /// <param name="newkey"></param>
        /// <param name="fromkey"></param>
        /// <param name="keys"></param>
        public void StoreDifferencesFromSet(string newkey, string fromkey, string[] keys)
        {
            base.iClient.StoreDifferencesFromSet(newkey, fromkey, keys);
        }

        #endregion

    }
}

上面的代码创建完成后,项目的基础就构建完成了,下面开始学习set数据类型常用api的使用。

在控制台应用程序中的ServiceStackTest.cs类中,调用Redis的api方法。代码如下:

 

using MyRedis.Redis.Service;
using System;
using System.Collections.Generic;
using System.Threading;

namespace MyRedis
{
    /// <summary>
    /// ServiceStackTest api 封装测试
    /// </summary>
    public class ServiceStackTest
    {
        public class Student
        {
            public int Id { get; set; }
            public string Name { get; set; }
            public string Remark { get; set; }
            public int Age { get; set; }
        }

        public static void Show()
        {
            #region RedisSetService

            using (RedisSetService setService = new RedisSetService())
            {
                setService.FlushAll();

                //模拟zhangsan和lisi的好友列表
                setService.AddItemToSet("zhangsan", "lisi");
                setService.AddItemToSet("zhangsan", "jack");
                setService.AddItemToSet("zhangsan", "jam");
                setService.AddItemToSet("zhangsan", "alis");
                setService.AddItemToSet("zhangsan", "wangwu");


                setService.AddItemToSet("lisi", "zhangsan");
                setService.AddItemToSet("lisi", "lucy");
                setService.AddItemToSet("lisi", "wangwu");


                var res1 = setService.GetIntersectFromSets("zhangsan", "lisi");//交集
                var res2 = setService.GetDifferencesFromSet("zhangsan", "lisi");//差集 前者有,后者没有的
                var res3 = setService.GetUnionFromSets("zhangsan", "lisi");//并集 两者所有的合起来
                
                Console.WriteLine("************** 交集 ******************");
                foreach (var item in res1)
                {
                    Console.WriteLine(item);
                }

                Console.WriteLine("************** 差集 ******************");
                foreach (var item in res2)
                {
                    Console.WriteLine(item);
                }

                Console.WriteLine("************** 并集 ******************");
                foreach (var item in res3)
                {
                    Console.WriteLine(item);
                }            
            }

            #endregion

        }
    }
}

执行结果:

Redis分布式缓存学习总结4(set数据类型) 

 

执行后可以从可视化工具看到Redis中存储的数据信息:

Redis分布式缓存学习总结4(set数据类型)

 

Redis分布式缓存学习总结4(set数据类型)

通过上文,我们可以知道集合的主要几个特性,无序、不可重复、支持并交差等操作。因此集合类型比较适合用来数据去重和保障数据的唯一性,还可以用来统计多个集合的交集、错集和并集等,当我们存储的数据是无序并且需要去重的情况下,比较适合使用集合类型进行存储。

更多hash的用法,参考文章:https://www.cnblogs.com/hunternet/p/12695738.html

上一篇:python - 连接redis


下一篇:Linux 输入设备 自定义键盘 input输入子系统 gpio-keys按键驱动