Redis
2020-08-01 22:56
1026 查看
Redis
-
概念: redis是一款高性能的NOSQL系列的非关系型数据库
-
什么是Redis
Redis是用C语言开发的一个开源的高性能键值对(key-value)数据库,官方提供测试数据,50个并发执行100000个请求,读的速度是110000次/s,写的速度是81000次/s ,且Redis通过提供多种键值数据类型来适应不同场景下的存储需求。-
目前为止Redis支持的键值数据类型如下:
1) 字符串类型 string
2) 哈希类型 hash
3) 列表类型 list
4) 集合类型 set
5) 有序集合类型 sortedset - redis的应用场景
• 缓存(数据查询、短连接、新闻内容、商品内容等等)
• 聊天室的在线好友列表
• 任务队列。(秒杀、抢购、12306等等)
• 应用排行榜
• 网站访问统计
• 数据过期处理(可以精确到毫秒
• 分布式集群架构中的session分离 -
命令操作
redis的数据结构:
-
redis存储的是:key,value格式的数据,其中key都是字符串,value有5种不同的数据结构
* value的数据结构:
1) 字符串类型 string
2) 哈希类型 hash : map格式
3) 列表类型 list : linkedlist格式。支持重复元素
4) 集合类型 set : 不允许重复元素
5) 有序集合类型 sortedset:不允许重复元素,且元素有顺序 -
字符串类型 string
存储: set key value
127.0.0.1:6379> set username zhangsan
OK - 获取: get key
127.0.0.1:6379> get username
“zhangsan” - 删除: del key
127.0.0.1:6379> del age
(integer) 1
哈希类型 hash
-
存储: hset key field value
127.0.0.1:6379> hset myhash username lisi
(integer) 1
127.0.0.1:6379> hset myhash password 123
(integer) 1
* hget key field: 获取指定的field对应的值
127.0.0.1:6379> hget myhash username
“lisi”
* hgetall key:获取所有的field和value
127.0.0.1:6379> hgetall myhash
1) “username”
2) “lisi”
3) “password”
4) “123”
127.0.0.1:6379> hdel myhash username
(integer) 1
列表类型 list:可以添加一个元素到列表的头部(左边)或者尾部(右边)
-
添加:
1. lpush key value: 将元素加入列表左边
2. rpush key value:将元素加入列表右边
127.0.0.1:6379> lpush myList a
(integer) 1
127.0.0.1:6379> lpush myList b
(integer) 2
127.0.0.1:6379> rpush myList c
(integer) 3
* lrange key start end :范围获取
127.0.0.1:6379> lrange myList 0 -1
1) “b”
2) “a”
3) “c”
* lpop key: 删除列表最左边的元素,并将元素返回
* rpop key: 删除列表最右边的元素,并将元素返回
集合类型 set : 不允许重复元素
-
存储:sadd key value
127.0.0.1:6379> sadd myset a
(integer) 1
127.0.0.1:6379> sadd myset a
(integer) 0
127.0.0.1:6379> smembers myset
1) “a”
127.0.0.1:6379> srem myset a
(integer) 1
有序集合类型 sortedset:不允许重复元素,且元素有顺序.每个元素都会关联一个double类型的分数。redis正是通过分数来为集合中的成员进行从小到大的排序。
-
存储:zadd key score value
127.0.0.1:6379> zadd mysort 60 zhangsan
(integer) 1
127.0.0.1:6379> zadd mysort 50 lisi
(integer) 1
127.0.0.1:6379> zadd mysort 80 wangwu
(integer) 1
127.0.0.1:6379> zrange mysort 0 -1
1) “lisi”
2) “zhangsan”
3) “wangwu”
127.0.0.1:6379> zrange mysort 0 -1 withscores
1) “zhangsan”
2) “60”
3) “wangwu”
4) “80”
5) “lisi”
6) “500”
127.0.0.1:6379> zrem mysort lisi
(integer) 1
通用命令
1. keys * : 查询所有的键
2. type key : 获取键对应的value的类型
3. del key:删除指定的key value
持久化
-
redis是一个内存数据库,当redis服务器重启,获取电脑重启,数据会丢失,我们可以将redis内存中的数据持久化保存到硬盘的文件中。
* 在一定的间隔时间中,检测key的变化情况,然后持久化数据 编辑redis.windwos.conf文件
# after 900 sec (15 min) if at least 1 key changed
save 900 1
# after 300 sec (5 min) if at least 10 keys changed
save 300 10
# after 60 sec if at least 10000 keys changed
save 60 10000
D:\JavaWeb2018\day23_redis\资料\redis\windows-64\redis-2.8.9>redis-server.exe redis.windows.conf
-
编辑redis.windwos.conf文件
appendonly no(关闭aof) --> appendonly yes (开启aof)
# appendfsync always : 每一次操作都进行持久化
appendfsync everysec : 每隔一秒进行一次持久化
# appendfsync no : 不进行持久化
Java客户端: Jedis
- Jedis: 一款java操作redis数据库的工具.
* 使用步骤:-
下载jedis的jar包
- 使用
/** * jedis的测试类 */ public class JedisTest { /* * 快速入门 * */ @Test public void test1(){ //1 获取连接 Jedis jedis = new Jedis("localhost",6379); //redis用的默认端口 //2 操作 jedis.set("username","zhangsan"); //3 关闭连接 jedis.close(); } }
- Jedis操作各种redis中的数据结构
public class JedisTest { /*String数据结构操作*/ @Test public void test2(){ //1 获取连接 Jedis jedis = new Jedis(); //如果使用空参,默认值localhost,6379端口 //2 操作 //存储 jedis.set("username","zhangsan"); //获取 String username = jedis.get("username"); System.out.println(username); //可以使用setex()方法存储可以指定过期的时间key value jedis.setex("acticecode",20,"hehe");//将acticecode:"hehe键值对存入jedis,并且20秒后自动删除" //3 关闭连接 jedis.close(); } /*Hash数据结构操作*/ @Test public void test3(){ //1 获取连接 Jedis jedis = new Jedis(); //如果使用空参,默认值localhost,6379端口 //2 操作 jedis.hset("user","name","lisi"); jedis.hset("user","age","23"); jedis.hset("user","gender","fmale"); //获取hash String name = jedis.hget("user", "name"); System.out.println(name); //获取hash中所有map中的数据 Map<String, String> user = jedis.hgetAll("user"); //遍历map集合 Set<String> set = user.keySet(); for (String key : set) { String value = user.get(key); System.out.println("key:"+key+",value:"+value); } //3 关闭连接 jedis.close(); } /*List数据结构操作 允许重复存储*/ @Test public void test4(){ //1 获取连接 Jedis jedis = new Jedis(); //如果使用空参,默认值localhost,6379端口 //2 操作 //存储 jedis.lpush("mylist","a","b","c"); //从左边存 jedis.rpush("mylist","a","b","c"); //从右边存 //范围获取 List<String> mylist = jedis.lrange("mylist", 0, -1); System.out.println(mylist); //[c, b, a, a, b, c] //list 弹出 String element1 = jedis.lpop("mylist"); //c 从左弹出 System.out.println(element1); String element2 = jedis.rpop("mylist"); //c 从右弹出 System.out.println(element2); mylist = jedis.lrange("mylist", 0, -1); System.out.println(mylist); //[b, a, a, b] //3 关闭连接 jedis.close(); } /*Set数据结构操作 不允许重复*/ @Test public void test5(){ //1 获取连接 Jedis jedis = new Jedis(); //如果使用空参,默认值localhost,6379端口 //2 操作 //存储 jedis.sadd("myset","java","php","c++"); //获取 Set<String> set = jedis.smembers("myset"); System.out.println(set); //[c++, java, php] //3 关闭连接 jedis.close(); } /*sortedset数据结构操作 --- 排序*/ @Test public void test6(){ //1 获取连接 Jedis jedis = new Jedis(); //如果使用空参,默认值localhost,6379端口 //2 操作 //存储 jedis.zadd("mysortedset",3,"亚瑟"); jedis.zadd("mysortedset",30,"后裔"); jedis.zadd("mysortedset",25,"孙悟空"); //获取 Set<String> mysortedset = jedis.zrange("mysortedset", 0, -1); System.out.println(mysortedset); //[亚瑟, 孙悟空, 后裔] //3 关闭连接 jedis.close(); } }
jedis连接池: JedisPool
- 使用:
-
创建JedisPool连接池对象
- 调用方法 getResource()方法获取Jedis连接
/*jedis连接池使用*/ @Test public void test7(){ //0 创建配置对象 JedisPoolConfig config = new JedisPoolConfig(); config.setMaxTotal(50); //最大允许连接数 config.setMaxIdle(10);//最大空闲连接 //1 创建jedis连接池对象 // JedisPool jedisPool = new JedisPool(); JedisPool jedisPool = new JedisPool(config,"localhost",6379); //2 获取连接 Jedis jedis = jedisPool.getResource(); //3 使用 jedis.set("hehe","heihei"); //关闭,归还连接 jedis.close(); }
- 连接池工具类
/* * Jedis工具类 * 加载配置文件,配置连接池的参数 * 提供获取连接的方法 * */ public class JedisPoolUtil { private static JedisPool jedisPool; static { //读取配置文件 InputStream is = JedisPoolUtil.class.getClassLoader().getResourceAsStream("jedis.properties"); //创建Properties对象 Properties pro = new Properties(); //关联文件 try { pro.load(is); } catch (IOException e) { e.printStackTrace(); } //获取数据,设置到JedisPoolConfig中 JedisPoolConfig config = new JedisPoolConfig(); config.setMaxTotal(Integer.parseInt(pro.getProperty("maxTotal"))); config.setMaxIdle(Integer.parseInt(pro.getProperty("maxIdle"))); //初始化JedisPool jedisPool = new JedisPool(config,pro.getProperty("host"),Integer.parseInt(pro.getProperty("port"))); } /* * 获取连接的方法 * */ public static Jedis getJedis(){ return jedisPool.getResource(); } }
/*jedis工具类使用*/ @Test public void test8(){ //通过连接池工具类获取 Jedis jedis = JedisPoolUtil.getJedis(); jedis.set("hello","world"); jedis.close(); }
案例
- 案例需求:
1. 提供index.html页面,页面中有一个省份 下拉列表
2. 当 页面加载完成后 发送ajax请求,加载所有省份 - 注意:使用redis缓存一些不经常发生变化的数据
* 数据库的数据一旦发生改变,则需要更新缓存。
* 数据库的表执行 增删改的相关操作,需要将redis缓存数据情况,再次存入
* 在service对应的增删改方法中,将redis数据删除。
//前端 <head> <meta charset="UTF-8"> <title>Title</title> <script src="js/jquery-3.3.1.js"></script> <script> $(function () { //1 发生ajax请求加载所有省份的数据 $.get("provinceServlet",{},function (data) { // [{"id":1,"name":"北京"},{"id":2,"name":"上海"},{"id":3,"name":"广州"},{"id":4,"name":"陕西"}] //1 获取select var province = $("#province"); //2 遍历json数组 $(data).each(function () { //3 创建<option> var option = "<option name='"+this.id+"'>"+this.name+"</option>"; //4 调用select的append追加option province.append(option); }); }); }); </script> </head> <body> <select id="province"> <option>--请选择省份--</option> </select> </body>
//操作数据库dao public class ProvinceDaoImpl implements ProvinceDao { //1 声明成员变量 private JdbcTemplate template = new JdbcTemplate(JDBCUtils.getDataSource()); @Override public List<Province> finaAll() { //2 定义sql String sql = "select * from province"; //3 执行sql List<Province> list = template.query(sql, new BeanPropertyRowMapper<Province>(Province.class)); return list; } }
//Service public class ProvinceServiceImpl implements ProvinceService { //1 声明dao private ProvinceDao dao = new ProvinceDaoImpl(); //查询数据库数据 @Override public List<Province> finaAll() { return dao.finaAll(); } /*使用redis缓存*/ @Override public String findAllJson() { //1 先从redis中查询数据 //1.1获取redis客户端连接 Jedis jedis = JedisPoolUtil.getJedis(); String province_json = jedis.get("province"); //2 判断province_json是否为null if(province_json == null || province_json.length()==0){ //redis中没有数据 System.out.println("redis中没有数据,查询数据库"); //2.1查询数据库 List<Province> ps = dao.finaAll(); //2.2将list序列化为json ObjectMapper mapper = new ObjectMapper(); try { province_json = mapper.writeValueAsString(ps); //查询后赋值 } catch (JsonProcessingException e) { e.printStackTrace(); } //2.3 将json数据存入redis jedis.set("province",province_json); jedis.close(); //归还连接 }else { System.out.println("redis中有数据,查询缓存"); } return province_json; } }
//Servlet @WebServlet("/provinceServlet") public class ProvinceServlet extends HttpServlet { protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { /* //1 调用service执行 ProvinceService service = new ProvinceServiceImpl(); List<Province> list = service.finaAll(); //2 序列化list为json ObjectMapper mapper = new ObjectMapper(); String json = mapper.writeValueAsString(list);*/ //1 调用service执行 ProvinceService service = new ProvinceServiceImpl(); String json = service.findAllJson(); System.out.println(json); //3 响应结果 response.setContentType("application/json;charset=utf-8"); response.getWriter().write(json); } ... }
效果:
相关文章推荐
- redis-cli参数
- redis
- redis数据过期策略【转】
- redis持久化,主从及数据备份
- redis菜鸟教程
- Redis的AOF功能
- Redis实践(四)高可用的集群+哨兵部署 下的jedis开发
- Redis 配置(redis.conf)说明
- 持久化redis有几种方式?
- php7下安装redis扩展以及php操作redis
- Spring boot + redis 实现session 共享管理
- Redis介绍与入门
- Redis事务
- Redis学习总结(2)之Redis数据结构
- Unable to connect to Redis; nested exception is io.lettuce.core.RedisConnectionException: 我的解决办法
- Redis的安装及使用
- Redis的AOF功能
- Step into Redis- 09 - 主从复制
- redis-3.0.1 sentinel 主从高可用 详细配置
- 一个简单的log4j2的redis appender ,依赖于Jedis (A simple log4j2 redis appender which uses Jedis)