Redis series (II) 8 data types of redis

Time:2021-9-21

It is more or less used in NoSQL development, and it is also a necessary knowledge point for interview. I’ve asked every interview in recent days. However, I feel that the answer is not good, and there are still many knowledge points that need to be sorted out. Here, I’ll comb through several redis notes, and then add the above test questions.

Redis series:

  1. Redis series (I) introduction to redis
  2. Redis series (II) 8 data types of redis
  3. Redis series (III) integration of redis transactions and spring boot
  4. Redis series (IV) redis profile and persistence
  5. Redis series (V) publish subscribe mode, master-slave replication and sentinel mode
  6. Redis series (VI) redis’s cache penetration, cache breakdown and cache avalanche
  7. Redis series (VII) redis interview questions
  8. Redis Command Reference

1. Five data types of redis

The command can be viewed on the official website:http://www.redis.cn/commands.html

Redis-key

127.0.0.1:6379> keys *
(empty list or set)
127.0.0.1:6379> set name xxx
OK
127.0.0.1:6379> keys *
1) "name"
127.0.0.1:6379> set age 1
OK
127.0.0.1:6379> keys *
1) "age"
2) "name"
127.0.0.1:6379> exists name 		#  Determine whether the key exists
(integer) 1
127.0.0.1:6379> exists name1
(integer) 0
127.0.0.1:6379> move name 1
(integer) 1
127.0.0.1:6379> keys *
1) "age"
127.0.0.1:6379> set name yyy
OK
127.0.0.1:6379 > expire name 10 # sets the expiration time of the key, in seconds
(integer) 1
127.0.0.1:6379> ttl name 		#  View the remaining expiration time of the current key
(integer) 7
127.0.0.1:6379> ttl name
(integer) -2
127.0.0.1:6379> type age 		#  View the type of current key
string
127.0.0.1:6379>

Redis has the following five basic data types

1. String (string)

127.0.0.1:6379> set key1 v1 			# Set value
OK
127.0.0.1:6379> get key1
"v1"
127.0.0.1:6379> append key1 "hello" 		#  The additional value, if it does not exist, is equivalent to set key
(integer) 7
127.0.0.1:6379> get key1
"v1hello"
127.0.0.1:6379> strlen key1 		#  Get string length
(integer) 7
127.0.0.1:6379>

Self increasing and self decreasing

127.0.0.1:6379> set views 0
OK
127.0.0.1:6379> get views
"0"
127.0.0.1:6379> incr views 		#  Self increment 1
(integer) 1
127.0.0.1:6379> get views
"1"
127.0.0.1:6379 > decr views # minus 1
(integer) 0
127.0.0.1:6379> decr views
(integer) -1
127.0.0.1:6379> get views
"-1"
127.0.0.1:6379> incrby views 10 		#  Set step size, self increment 10 
(integer) 9
127.0.0.1:6379 > decrby views 5 # set step size and decrease by 5
(integer) 4

String range

127.0.0.1:6379> set key1 "hello,world!"
OK
127.0.0.1:6379> get key1
"hello,world!"
127.0.0.1:6379> getrange key1 0 3 		#  Intercept string [0, 3]
"hell"
127.0.0.1:6379> getrange key1 0 -1 		#  Get all strings, the same as get key
"hello,world!"
127.0.0.1:6379>

Replace:

127.0.0.1:6379> set key2 abcdefg
OK
127.0.0.1:6379> get key2
"abcdefg"
127.0.0.1:6379> setrange key2 1 xx
(integer) 7
127.0.0.1:6379> get key2
"axxdefg"
127.0.0.1:6379>

setex(set with expire): set expiration time

andsetnx(set if not exist): there is no reset (often used in distributed locks)

127.0.0.1:6379> setex key3 30 "hello" 		#  Set to expire in 30 seconds
OK
127.0.0.1:6379> ttl key3 					#  Remaining expiration time
(integer) 25
127.0.0.1:6379> setnx mykey "redis" 			#  Setting succeeded when MyKey does not exist
(integer) 1
127.0.0.1:6379> keys *
1) "key2"
2) "key1"
3) "views"
4) "mykey"
127.0.0.1:6379> setnx mykey "mongoDB" 		#  Setting failed when MyKey exists
(integer) 0
127.0.0.1:6379> get mykey 					#  MyKey value unchanged
"redis"
127.0.0.1:6379>

msetandmget

127.0.0.1:6379> mset k1 v1 k2 v2 k3 v3 		#  Set multiple values at the same time
OK
127.0.0.1:6379> keys *
1) "k1"
2) "k3"
3) "k2"
127.0.0.1:6379> mget k1 k2 k3 			#  Get multiple values at the same time
1) "v1"
2) "v2"
3) "v3"
127.0.0.1:6379 > msetnx K1 V1 K4 V4 # msetnx is an atomic operation that either succeeds or fails together
(integer) 0
127.0.0.1:6379> get k4
(nil)
127.0.0.1:6379>

object

Set user: 1 {Name: Zhangsan, age: 3} # set the value of a user: 1 object as JSON character to save an object

127.0.0.1:6379> mset user:1:name zhangsan user:1:age 2
OK
127.0.0.1:6379> mget user:1:name user:1:age
1) "zhangsan"
2) "2"
127.0.0.1:6379>

getset: get before set

127.0.0.1:6379> getset db redis 		#  Nil if no value exists
(nil)
127.0.0.1:6379> get db
"redis"
127.0.0.1:6379> getset db mongodb 		#  If a value exists, get the original value and set a new value
"redis"
127.0.0.1:6379> get db
"mongodb"
127.0.0.1:6379>

Usage scenario of string: value can be a number in addition to a string

  • Counter
  • Count multi unit quantity
  • Number of fans
  • Object cache storage

2. List

Basic data types, lists.

In redis, list can be used as stack, queue and blocking queue.

Most of the list commands arelstart.

127.0.0.1:6379> lpush list one 			#  Insert one or more values into the header of the list (left)
(integer) 1
127.0.0.1:6379> lpush list two
(integer) 2
127.0.0.1:6379> lpush list three 
(integer) 3
127.0.0.1:6379> lrange list 0 -1 			#  View all elements
1) "three"
2) "two"
3) "one"
127.0.0.1:6379> lrange list 0 1 				#  Get value through interval
1) "three"
2) "two"
127.0.0.1:6379> rpush list right 			#  Insert one or more values at the end of the list (right)
(integer) 4
127.0.0.1:6379> lrange list 0 -1
1) "three"
2) "two"
3) "one"
4) "right"
127.0.0.1:6379>

Pop up pop

127.0.0.1:6379> lrange list 0 -1
1) "!"
2) "world"
3) "world"
4) "hello"
127.0.0.1:6379> lpop list 		#  Remove the first element of the list
"!"
127.0.0.1:6379> lrange list 0 -1
1) "world"
2) "world"
3) "hello"
127.0.0.1:6379> rpop list 			#  Remove the first element of the list
"hello"
127.0.0.1:6379> lrange list 0 -1
1) "world"
2) "world"
127.0.0.1:6379>

Index lindex

127.0.0.1:6379> lrange list 0 -1
1) "hjk"
2) "world"
3) "world"
127.0.0.1:6379> lindex list 1 		#  Get a value in the list by subscript
"world"
127.0.0.1:6379> lindex list 0
"hjk"
127.0.0.1:6379>

Llen length:

127.0.0.1:6379> llen list
(integer) 3
127.0.0.1:6379>

Remove specified value:

127.0.0.1:6379> lrange list 0 -1
1) "hjk"
2) "world"
3) "world"
127.0.0.1:6379> lrem list 1 world 		#  Remove the specified number of values in the list collection and match them exactly
(integer) 1
127.0.0.1:6379> lrange list 0 -1
1) "hjk"
2) "world"
127.0.0.1:6379> lpush list hjk
(integer) 3
127.0.0.1:6379> lrange list 0 -1
1) "hjk"
2) "hjk"
3) "world"
127.0.0.1:6379> lrem list 2 hjk
(integer) 2
127.0.0.1:6379> lrange list 0 -1
1) "world"
127.0.0.1:6379>

Trim truncation

127.0.0.1:6379> lrange mylist 0 -1
1) "hello1"
2) "hello2"
3) "hello3"
4) "hello4"
127.0.0.1:6379 > ltrim mylist 1 2 # intercepts the specified length through the subscript. The list has been destroyed and only the truncated elements are left after truncation
OK
127.0.0.1:6379> lrange mylist 0 -1
1) "hello2"
2) "hello3"
127.0.0.1:6379>

Rpop lpush: removes the last element of the list and moves it to a new list.

127.0.0.1:6379> lrange mylist 0 -1
1) "hello1"
2) "hello2"
3) "hello3"
127.0.0.1:6379> rpoplpush mylist myotherlist 		#  Remove the last element of the list and move it to a new list.
"hello3"
127.0.0.1:6379> lrange mylist 0 -1 		#  View the original list
1) "hello1"
2) "hello2"
127.0.0.1:6379> lrange myotherlist 0 -1 		#  Check that the value does exist in the target list
1) "hello3"
127.0.0.1:6379>

Lset: replace the value of the specified subscript in the list with another value to update the operation

127.0.0.1:6379> exists list 		#  Determine whether this list exists
(integer) 0
127.0.0.1:6379> lset list 0 item 		#  If it does not exist, the update will report an error
(error) ERR no such key
127.0.0.1:6379> lpush list value1
(integer) 1
127.0.0.1:6379> lrange list 0 0 
1) "value1"
127.0.0.1:6379> lset list 0 item 		#  If present, update the value of the current subscript
OK
127.0.0.1:6379> lset list 1 other 		#  If it does not exist, the update will report an error
(error) ERR index out of range
127.0.0.1:6379>

Linsert: insert a specific value before or after an element in the list

127.0.0.1:6379> lrange mylist 0 -1
1) "hello1"
2) "hello2"
127.0.0.1:6379> linsert mylist before "hello2" hello
(integer) 3
127.0.0.1:6379> lrange mylist 0 -1
1) "hello1"
2) "hello"
3) "hello2"
127.0.0.1:6379> linsert mylist after "hello2" hello
(integer) 4
127.0.0.1:6379> lrange mylist 0 -1
1) "hello1"
2) "hello"
3) "hello2"
4) "hello"
127.0.0.1:6379>

Summary

  • List is actually a linked list, which can be inserted before and after
  • If the key does not exist, create a new linked list
  • If all values are removed, the empty linked list also means that it does not exist
  • Inserting or changing values on both sides is the most efficient.

3. Set

127.0.0.1:6379> sadd myset "hello" 		#  Add element to set set
(integer) 1
127.0.0.1:6379> sadd myset "world"		
(integer) 1
127.0.0.1:6379> smembers myset 		    #  View all values of the specified set
1) "world"
2) "hello"
127.0.0.1:6379> sismember myset hello 		#  Determine whether a value is in set
(integer) 1
127.0.0.1:6379> sismember myset hello1
(integer) 0
127.0.0.1:6379>
127.0.0.1:6379> scard myset 		#  Gets the number of in the collection
(integer) 2
127.0.0.1:6379> sadd myset "hello2"		
(integer) 1
127.0.0.1:6379> smembers myset   
1) "world"
2) "hello2"
3) "hello"
127.0.0.1:6379 > SREM myset Hello # remove element
(integer) 1
127.0.0.1:6379> smembers myset
1) "world"
2) "hello2"
127.0.0.1:6379>
127.0.0.1:6379> smembers myset
1) "kkk"
2) "world"
3) "hjk"
4) "hello2"
127.0.0.1:6379> srandmember myset 			#  Randomly extract an element
"hjk"
127.0.0.1:6379> srandmember myset
"hello2"
127.0.0.1:6379> srandmember myset 2 			#  Randomly extract a specified number of elements
1) "world"
2) "hello2"
127.0.0.1:6379> srandmember myset 2
1) "hello2"
2) "hjk"
127.0.0.1:6379>
127.0.0.1:6379> smembers myset
1) "kkk"
2) "world"
3) "hjk"
4) "hello2"
127.0.0.1:6379> spop myset 		#  Randomly delete elements
"hjk"
127.0.0.1:6379> smembers myset
1) "kkk"
2) "world"
3) "hello2"
127.0.0.1:6379> spop myset
"hello2"
127.0.0.1:6379> smembers myset
1) "kkk"
2) "world"
127.0.0.1:6379>
127.0.0.1:6379> smembers myset
1) "kkk"
2) "world"
127.0.0.1:6379> sadd myset2 set2
(integer) 1
127.0.0.1:6379> smove myset myset2 "kkk" 			#  Move a specific value to another set set
(integer) 1
127.0.0.1:6379> smembers myset
1) "world"
127.0.0.1:6379> smembers myset2
1) "kkk"
2) "set2"
127.0.0.1:6379>
127.0.0.1:6379> smembers key1
1) "b"
2) "a"
3) "c"
127.0.0.1:6379> smembers key2
1) "e"
2) "d"
3) "c"
127.0.0.1:6379> sdiff key1 key2 			#  Difference set
1) "b"
2) "a"
127.0.0.1:6379 > sinter key1 key2 # intersection
1) "c"
127.0.0.1:6379> sunion key1 key2 		#  Union
1) "e"
2) "a"
3) "c"
4) "d"
5) "b"

4. Hash (hash)

It is also in the form of key – value, but value is a map.

127.0.0.1:6379> hset myhash field xxx 		#  Set a key value
(integer) 1
127.0.0.1:6379> hget myhash field 			#  Get a field value
"xxx"
127.0.0.1:6379> hmset myhash field1 hello field2 world 		#  Set multiple key values
OK
127.0.0.1:6379> hmget myhash field field1 field2 			#  Get multiple field values
1) "xxx"
2) "hello"
3) "world"
127.0.0.1:6379> hgetall myhash 				#  Get all the data
1) "field"
2) "xxx"
3) "field1"
4) "hello"
5) "field2"
6) "world"
127.0.0.1:6379> hdel myhash field1 		#  Delete the specified key and the corresponding value will disappear
(integer) 1
127.0.0.1:6379> hgetall myhash
1) "field"
2) "xxx"
3) "field2"
4) "world"
127.0.0.1:6379>
127.0.0.1:6379> hlen myhash 		#  Get length
(integer) 2
127.0.0.1:6379 > hexists myhash field1 # determines whether the specified key exists
(integer) 0
127.0.0.1:6379> hexists myhash field2
(integer) 1
127.0.0.1:6379> hkeys myhash 		#  Get all keys
1) "field"
2) "field2"
127.0.0.1:6379> hvals myhash 		#  Get all values
1) "xxx"
2) "world"
127.0.0.1:6379>
127.0.0.1:6379> hset myhash field3 5		
(integer) 1
127.0.0.1:6379> hincrby myhash field3 1 		#  Specify increment
(integer) 6
127.0.0.1:6379> hincrby myhash field3 -1
(integer) 5
127.0.0.1:6379> hsetnx myhash field4 hello 		#  If it does not exist, it can be set
(integer) 1
127.0.0.1:6379> hsetnx myhash field4 world 		#  If it exists, it cannot be set
(integer) 0
127.0.0.1:6379>

Hash is suitable for storing frequently changing object information, and string is more suitable for storing strings.

5. Zset (ordered set)

127.0.0.1:6379> zadd myset 1 one 		#  Add a value
(integer) 1
127.0.0.1:6379> zadd myset 2 two 3 three 	#  Add multiple values
(integer) 2
127.0.0.1:6379> zrange myset 0 -1
1) "one"
2) "two"
3) "three"
127.0.0.1:6379>

Implement sorting:

127.0.0.1:6379> zadd salary 2500 xiaohong
(integer) 1
127.0.0.1:6379> zadd salary 5000 xiaoming
(integer) 1
127.0.0.1:6379> zadd salary 500 xaiozhang
(integer) 1
127.0.0.1:6379> zrange salary 0 -1
1) "xaiozhang"
2) "xiaohong"
3) "xiaoming"
127.0.0.1:6379> zrangebyscore salary -inf +inf 		#  Display all users from small to large
1) "xaiozhang"
2) "xiaohong"
3) "xiaoming"
127.0.0.1:6379> zrevrange salary 0 -1 		#  Sort from large to small
1) "xiaoming"
2) "xiaohong"
3) "xaiozhang"
127.0.0.1:6379 > zrangebyscore salary - inf + inf withscores # attached display all users
1) "xaiozhang"
2) "500"
3) "xiaohong"
4) "2500"
5) "xiaoming"
6) "5000"
127.0.0.1:6379> zrangebyscore salary -inf 2500 withscores 			#  Show users with wages less than 2500
1) "xaiozhang"
2) "500"
3) "xiaohong"
4) "2500"
127.0.0.1:6379> zrange salary 0 -1
1) "xaiozhang"
2) "xiaohong"
3) "xiaoming"
127.0.0.1:6379 > zrem salary Xiaohong # removes specific elements
(integer) 1
127.0.0.1:6379> zrange salary 0 -1
1) "xaiozhang"
2) "xiaoming"
127.0.0.1:6379> zcard salary 		#  Gets the number of ordered collections
(integer) 2
127.0.0.1:6379>
127.0.0.1:6379> zadd myset 1 hello
(integer) 1
127.0.0.1:6379> zadd myset 2 world 3 !
(integer) 2
127.0.0.1:6379> zcount myset 1 3 		#  Gets the number of personnel in the specified interval
(integer) 3
127.0.0.1:6379> zcount myset 1 2
(integer) 2

2. Redis has three special data types

1、geospatial

Redis launched geo type in 3.2, which can calculate the geographic location information and the distance between the two places.

file:https://www.redis.net.cn/order/3687.html

Simulate some data with the help of the website:http://www.jsons.cn/lngcode/

Geoadd add geographic location

Rule: the two poles cannot be added directly. Generally, the city data will be downloaded and imported directly through the Java program at one time.

The effective longitude is from – 180 degrees to 180 degrees. The effective latitude ranges from -85.05112878 degrees to 85.05112878 degrees. When the coordinate position exceeds the specified range, the command will return an error.

(error) ERR invalid longitude latitude pair xxx yyy

Add some simulation data:

127.0.0.1:6379> geoadd china:city 116.40 39.90 beijing
(integer) 1
127.0.0.1:6379> geoadd china:city 121.47 31.23 shanghai
(integer) 1
127.0.0.1:6379> geoadd china:city 106.50 29.53 chongqing 114.05 22.52 shengzhen
(integer) 2
127.0.0.1:6379> geoadd china:city 120.16 30.24 hangzhou 108.96 34.26 xian
(integer) 2
127.0.0.1:6379>

Geopos obtains the current positioning coordinate value

127.0.0.1:6379> geopos china:city beijing 		#  Gets the latitude and longitude of the specified city
1) 1) "116.39999896287918091"
   2) "39.90000009167092543"
127.0.0.1:6379> geopos china:city shanghai
1) 1) "121.47000163793563843"
   2) "31.22999903975783553"
127.0.0.1:6379>

Geodist gets the distance between two locations

Company:

  • mIndicates in meters.
  • kmExpressed in kilometers.
  • miIndicates in miles.
  • ftIndicates in feet.

If the user does not explicitly specify the unit parameter, thenGEODISTThe default unit is meters.

127.0.0.1:6379> geodist china:city beijing shanghai km 	#  Check the direct straight-line distance between Beijing and Shanghai
"1067.3788"
127.0.0.1:6379> geodist china:city beijing chongqing km
"1464.0708"
127.0.0.1:6379>

Georadius takes the given latitude and longitude as the center to find the elements within a certain radius

127.0.0.1:6379 > georadius China: City 110, 30, 1000 km # take 110, 30 as the center and look for a city with an area of 1000 km
1) "chongqing"
2) "xian"
3) "shengzhen"
4) "hangzhou"
127.0.0.1:6379> georadius china:city 110 30 500 km 
1) "chongqing"
2) "xian"
127.0.0.1:6379> georadius china:city 110 30 500 km withcoord 	#   Display other people's location information
1) 1) "chongqing"
   2) 1) "106.49999767541885376"
      2) "29.52999957900659211"
2) 1) "xian"
   2) 1) "108.96000176668167114"
      2) "34.25999964418929977"
127.0.0.1:6379> 
127.0.0.1:6379 > geodius China: City 110 30 500 km withlist # displays the distance to the center point
1) 1) "chongqing"
   2) "341.9374"
2) 1) "xian"
   2) "483.8340"
127.0.0.1:6379 > geodius China: City 110 30 500 km withlist withgood count 1 # specified quantity
1) 1) "chongqing"
   2) "341.9374"
   3) 1) "106.49999767541885376"
      2) "29.52999957900659211"
127.0.0.1:6379> georadius china:city 110 30 500 km withdist withcoord count 2
1) 1) "chongqing"
   2) "341.9374"
   3) 1) "106.49999767541885376"
      2) "29.52999957900659211"
2) 1) "xian"
   2) "483.8340"
   3) 1) "108.96000176668167114"
      2) "34.25999964418929977"
127.0.0.1:6379>

Georadiusbymember finds other elements around the specified element

127.0.0.1:6379> georadiusbymember china:city shanghai 1000 km
1) "hangzhou"
2) "shanghai"
127.0.0.1:6379>

The underlying implementation principle of geo is actually Zset. You can use the Zset command to operate Geo

127.0.0.1:6379> zrange china:city 0 -1
1) "chongqing"
2) "xian"
3) "shengzhen"
4) "hangzhou"
5) "shanghai"
6) "beijing"
127.0.0.1:6379> zrem china:city beijing 		#  Delete an element
(integer) 1
127.0.0.1:6379> zrange china:city 0 -1
1) "chongqing"
2) "xian"
3) "shengzhen"
4) "hangzhou"
5) "shanghai"
127.0.0.1:6379>

2、hyperloglog

Cardinality: the number of elements in a mathematical set. It cannot be repeated.

UV (unique visitor): refers to the natural person who accesses and browses this web page through the Internet. A computer client visited is a visitor, and the same visitor is calculated only once a day.

Redis version 2.8.9 updates the hyperloglog data structure, which is an algorithm based on cardinality statistics.

The advantage of hyperloglog is that it occupies less memory and is fixed. It only needs 12 KB to store the cardinality of 2 ^ 64 different elements. However, there may be an error rate of 0.81%.

This data structure is often used to count the UV of websites. The traditional way is to use set to save the user’s ID, and then count the number of elements in set as the judgment standard. However, this method saves a large number of user IDs, which are generally long, occupy space and troublesome. Our goal is to count, not to save data, so this has disadvantages. However, it is more appropriate to use hyperloglog.

127.0.0.1:6379> pfadd mykey a b c d e f g h i j 	#  Create the first set of elements
(integer) 1
127.0.0.1:6379> PFCOUNT mykey 					#  Statistics MyKey cardinality
(integer) 10
127.0.0.1:6379 > pfadd mykey2 I j Z x C v b n m # create the second set of elements
(integer) 1
127.0.0.1:6379> PFCOUNT mykey2 					#  Statistical mykey2 cardinality
(integer) 9
127.0.0.1:6379> PFMERGE mykey3 mykey mykey2 		#  Merge two groups MyKey mykey2 = > mykey3
OK
127.0.0.1:6379> PFCOUNT mykey3
(integer) 15
127.0.0.1:6379>

3. Bitmap

Bitmap is to set 0 or 1 through the smallest unit bit to represent the value or state corresponding to an element. The value of a bit, either 0 or 1; In other words, the maximum information that a bit can store is 2.

Bitmap is often used to count user information, such as active and inactive fans, logged in and not logged in, whether to punch in or not, etc.

Here is a case of clocking in one week to illustrate its usage:

127.0.0.1:6379> setbit sign 0 1 		#  Clock in on Monday
(integer) 0
127.0.0.1:6379> setbit sign 1 0 		#  Didn't punch in on Tuesday
(integer) 0
127.0.0.1:6379> setbit sign 2 0 		#  Didn't punch in on Wednesday
(integer) 0
127.0.0.1:6379> setbit sign 3 1
(integer) 0
127.0.0.1:6379> setbit sign 4 1
(integer) 0
127.0.0.1:6379> setbit sign 5 1
(integer) 0
127.0.0.1:6379> setbit sign 6 0
(integer) 0
127.0.0.1:6379>

Check whether to clock in a day:

127.0.0.1:6379> GETBIT sign 3
(integer) 1
127.0.0.1:6379> GETBIT sign 6
(integer) 0
127.0.0.1:6379>

Statistics: counts the number of days clocked in

127.0.0.1:6379> BITCOUNT sign
(integer) 4
127.0.0.1:6379>

The next note will introduce redis transactions and spring boot integration.

Recommended Today

Seven Python code review tools recommended

althoughPythonLanguage is one of the most flexible development languages at present, but developers often abuse its flexibility and even violate relevant standards. So PythoncodeThe following common quality problems often occur: Some unused modules have been imported Function is missing arguments in various calls The appropriate format indentation is missing Missing appropriate spaces before and after […]