1、redis(非关系型数据库)
redis(非关系型数据库)
redis全称:reomote Dictionary Server (远程字典服务),是一个开源的,使用ANSI C语言来编写。是基于内存来存储key-value的数据库,还可以持久化的保存在磁盘上。redis是NoSQL类型的数据库的一种。支持大多数主流的开发,如java、c、python等。
NoSQL:(Not Only SQL)泛指非关系型数据。NoSQL不仅仅是一个概念,还泛指非关系型数据库,区别于关系型数据库,他们不保证ACID特性。NoSQL是一种全新的数据库革命性运动,能够解决关系型数据库难以完成的操作,还具有已扩展,高可读写的性能,特别是当数据量大的时候,同样表现优秀。
redis:key的 命名规范
- 以英文字母开头,命名只能出现小写字母、数字、英文点号(.)和英文的冒号(:)
- 不要包含特殊字符,如下划线、空格、换行、单双引号及其他转义字符
- 命名做到见名知意,key的长度不宜过长影响查询效率
redis的基本操作
redis默认有16个数据库。(默认选中0,名字从0开始)
切换数据库 select 1:这样就切换到名字为1的数据库
查看key:keys patten:patten是查询key的规则,使用*表示查看当前数据库中所有的key。
value的数据类型
redis中的key-value中的value也是有数据类型的。数据类型有String,List,Hash,Set,SortedSet。
String类型
常见的命令操作有如下:
set key value:设置一个key,值为value,值类型为String的键值对,若key不存在则创建,若key已存在,则更新value。返回 1成功,0失败。get key:获取key对应的value,若key不存在,则返回nil。mget key1 key2 key3:获取多个value。incr key:将key的数字加1,若key不存在则会创建一个,并初始化为0,然后数值加1。若key的value不是一个数字,则会报错。incr key increment:可以设置每次执行加的次数(increment)。decr key:将key的数值减1,若key不存在,先创建并初始化为0,再执行减1操作,若不存在则报错。decrby key increment:可以设置每次执行减的次数(increment)。append key value:若key存在,则在后面最加value,若key不存在,则执行set的操作。help @String:查看string类型的帮助文档。
String类型的应用场景:朋友圈的点赞,微博的点赞,直播的在线点赞等。
解决了多线程的问题:redis是单线程的,读写的速度非常快,不存在处理不过来的问题。比如窗口卖票是多线程的线程锁解决卖票的不一致问题,操作复杂。而redis却能简单的解决卖票的线程问题。
List类型
list类型使用的是一个双向链表的数据结构,只能对两边的数据进行增删。这样做到增删快的操作。添加还保持了顺序。
位置:从左往右是从0开始的。
从右往左是从-1开始的。
常见的命令操作有如下:
lpush key value1 value2 value3:从左边推进去,存入的顺序是value1,value2,value3,而在第一位的是value3。rpush key value1 value2:从右边开始推 值进去,如果key存在,则从右边开始存值进去,顺序是value1,value2,而value2的位置在-1。llen:返回key的list长度。lindex key index:根据下标查找元素,从0开始,从左往右。lrange key start stop:查找指定范围的key,如lrange key 0 -1,查询所有的key。lpop:从左边移除第一个元素,返回第一个元素。rpop:从右边移除第一个元素,返回移除的元素。(最后一个元素)
list类型使用场景:处理排名类的业务,楼层的回帖,聊天室等。
Hash类型(散列)
常用的命令如下:
hset key field value:设置hash field为指定值,若key不存在,则会创建,若key存在,则会更新数据。hget key field:获取指定的hash field。hmget key field...:获取指定多个的hash field。hmset key field value1...fieldN valueN:同时设置hash的多个field。hexists key field:判断指定的field是否存在,存在返回true,不存在返回false。hdel key field:删除指定的hash field。hlen key:返回指定hash的field数量。hkeys key:返回hash的所有field。hvals key:返回hash的所有value。hgetall key:返回hash的所有field和value。
hash的用途:
节约内存空间
redis每创建一个键(key),都会为这个键储存一些附加的管理信息(比如这个键的类型,这个键最后一次被访问的时间等等)
redis的key相对于值来说,更珍贵!!!
value类似于一个Map集合的数据结构。解决多条数据key前部分相同,而后面部分不同,比如装一个实体类pojo,装数据库中的一条记录,只需要一个key就可以了,而用字符串,则会使key的数量增加,影响查询效率。
不适用场景:
如果我们仅仅只对一个字段设置过期,就不建议使用hash。
Redis的key的过期功能只能对键操作,而Hash结构不能单独对某一个filed设置过期功能。
说明:在实际开发中,能使用hash的时候,尽量使用hash!!
Set类型
特点:
- 无序的、不可重复的
- 元素都是字符串类型
- 最多2^32-1元素
常用命令如下:
sadd key member[member...]:添加一个set类型的value,若key不存在则会创建,若key存在,如果是一个set类型的则将不同的添加进去,相同的则会被忽略,如果不是set类型,返回一个错误。smembers key:返回集合key中的所有成员。不存在的key则视为空集合。spop key:移除并返回集合中一个随机的元素。被移除的元素是随机的。当key不存在或key是空集时,返回nil。scard key:返回集合key的基数(集合元素的个数)。当key不存在时,返回0。sinter key[key...]:返回一个几个的全部成员,该集合是所有给定集合的交集。不存在视为空集。sunion key[key...]:返回一个集合的全部成员,该集合的所有给定集合的并集。不存在视为空集。sdiff key [key...]:返回一个集合的全部成员,该集合是所有第一个集合的差集。不存在视为空集。
应用场景:qq的共同好友,可能认识的人。新浪微博的共同关注等。
SortedSet类型
- 类似Set集合
- 有序的、不可重复的
- 元素类型是字符串类型
- 每一个元素都关联着一个浮点数分值(Score),可以按照分值进行排序,分值也可以相同。
- 最多包含2^32-1元素
常用的命令如下:
zadd key [sort member sort member...]:增加值,如zadd set1 1.0 zhangshan 2.0 lisizrange key start end:根据指定的索引查询范围的值。如zrange set1 0 -1zcout key start end:统计一个范围内元素的个数。根据分值查找。返回有序集 key 中, score 值在 min 和 max 之间(默认包括 score 值等于 min 或 max )的成员的数量。zcard key:统计元素的个数。如zcard set1。zrank key:返回成员的索引号。如zrank set1 lucyzrem key [member...]:删除成员。如zrem set1 zhangsan
适用场景:适用于需要有序且唯一的业务。
比如网易云音乐的排行榜。
Jedis连接Redis服务器
注意事项:必须要放开redis允许启动主机访问。
注释/etc/redis.conf 的 bind 127.0.0.1 这个句话 或者 设置为 bind *

项目结构

Jedis连接redis服务端
@Test
public void testJedis() {
// 连接redis
Jedis jedis = new Jedis("192.168.6.100", 6379);
// 连接密码
jedis.auth("root");
// ping
// System.out.println("ping : "+jedis.ping());//PONG
// System.out.println(jedis.info());
}
-
1)ip绑定问题
Connection refused: connect
![]()
把Redis的配置文件redis.conf里的
bind localhost(或者bind 127.0.0.1,表明只有该主机才能访问)注释掉。

或者修改为:
bind ip 表明,只能通过ip访问。
-
保护模式
DENIED Redis is running in protected mode because protected mode is enabled…
redis处于保护模式,只能本地链接,我们需要修改配置文件redis.conf,将protected-mode yes改成no

Key的测试
@Test
public void testJedis() {
// 连接redis
Jedis jedis = new Jedis("192.168.6.100", 6379);
// 连接密码
jedis.auth("root");
// ping
// System.out.println("ping : "+jedis.ping());//PONG
// System.out.println(jedis.info());
// 操作redis
jedis.flushAll();//删除当前所有的key-value
// ==============String类型=================
jedis.set("name", "lihua2");
String name = jedis.get("name");
System.out.println("name : " + name);// 返回OK
// jedis.incr("dz");
// System.out.println(jedis.get("dz"));
jedis.incrBy("dz", 10);
jedis.decr("dz");
// System.out.println(jedis.get("dz"));
// =================List类型=========================
jedis.lpush("boys", "孙悟空", "猪八戒", "唐僧", "白龙马", "沙僧");
List<String> boys = jedis.lrange("boys", 0, -1);
System.out.println(boys.getClass().getName());
System.out.println(boys);
// ==================hash类型========================
jedis.hset("users", "id", "1");
jedis.hset("users", "name", "悟空");
jedis.hset("users", "age", "1000");
String id = jedis.hget("users", "id");
System.out.println(id);
Map<String, String> users = jedis.hgetAll("users");
System.out.println(users.getClass().getName());
System.out.println(users);
// =====================set类型=================================
jedis.sadd("girls", "lili", "lucy", "lihua", "xiaohong");
jedis.sadd("girls2", "zhanjun", "lucy", "baibai", "xiaohong");
Set<String> sinter = jedis.sinter("girls", "girls2");
System.out.println(sinter.getClass().getName());
System.out.println(sinter);
// ========================sortedSet类型===============
jedis.zadd("fuirt", 1.0, "西瓜");
jedis.zadd("fuirt", 2.0, "蜜桃");
jedis.zadd("fuirt", 2.5, "香蕉");
jedis.zadd("fuirt", 3.0, "哈密瓜");
jedis.zadd("fuirt", 10.0, "娃娃菜");
Set<String> fuirt = jedis.zrangeByScore("fuirt", 1.0, 2.0);
System.out.println(fuirt.getClass().getName());
System.out.println(fuirt);
}


浙公网安备 33010602011771号