Python使用redis-py库连接Redis数据库
安装 redis - py 库
在使用 redis - py
库连接 Redis 数据库之前,首先需要确保该库已经安装在你的 Python 环境中。如果你使用的是 pip
包管理器,安装 redis - py
库非常简单,只需在命令行中执行以下命令:
pip install redis
如果你使用的是 conda
环境,可以使用以下命令进行安装:
conda install -c conda - forge redis
安装完成后,就可以在 Python 代码中引入 redis
模块来连接和操作 Redis 数据库了。
基本连接
在 Python 中使用 redis - py
连接 Redis 数据库,最基本的方式如下:
import redis
# 创建 Redis 连接对象
r = redis.Redis(host='localhost', port=6379, db = 0)
# 设置一个键值对
r.set('name', 'John')
# 获取键对应的值
name = r.get('name')
print(name.decode('utf - 8'))
在上述代码中:
- 首先通过
import redis
导入redis
模块。 - 然后使用
redis.Redis
类创建一个 Redis 连接对象r
。这里指定了 Redis 服务器的主机为localhost
(如果 Redis 服务器运行在其他主机上,需要替换为相应的主机地址),端口为默认的6379
,并选择使用db 0
数据库(Redis 支持多个逻辑数据库,编号从 0 开始)。 - 使用
r.set('name', 'John')
方法在 Redis 中设置一个键为name
,值为John
的键值对。 - 通过
r.get('name')
获取键name
对应的值。需要注意的是,redis - py
获取的值是字节类型,所以这里使用decode('utf - 8')
将其转换为字符串类型并打印出来。
连接池的使用
在实际应用中,尤其是在高并发的场景下,频繁地创建和销毁 Redis 连接是非常消耗资源的。为了提高性能和资源利用率,可以使用连接池。redis - py
提供了 ConnectionPool
类来实现连接池功能。以下是使用连接池的示例代码:
import redis
# 创建连接池
pool = redis.ConnectionPool(host='localhost', port=6379, db = 0)
# 通过连接池创建 Redis 连接对象
r = redis.Redis(connection_pool = pool)
# 设置一个键值对
r.set('age', 30)
# 获取键对应的值
age = r.get('age')
print(int(age))
在这个例子中:
- 首先创建了一个
ConnectionPool
对象pool
,同样指定了 Redis 服务器的主机、端口和数据库。连接池会预先创建一定数量的连接,并在需要时复用这些连接。 - 然后通过
redis.Redis(connection_pool = pool)
创建 Redis 连接对象r
,这样r
就会从连接池pool
中获取连接来执行 Redis 命令。
密码认证
如果你的 Redis 服务器设置了密码,在连接时需要进行密码认证。在 redis - py
中,认证非常简单,只需要在创建连接对象时传入 password
参数即可。示例代码如下:
import redis
# 创建 Redis 连接对象并进行密码认证
r = redis.Redis(host='localhost', port=6379, db = 0, password='your_password')
# 设置一个键值对
r.set('email', 'john@example.com')
# 获取键对应的值
email = r.get('email')
print(email.decode('utf - 8'))
在上述代码中,通过 password='your_password'
传入了 Redis 服务器的密码,这样才能成功连接并操作 Redis 数据库。
操作字符串类型数据
Redis 中的字符串类型是最基本的数据类型,redis - py
提供了丰富的方法来操作字符串类型的数据。
设置值
除了前面使用过的 set
方法外,redis - py
还提供了一些其他设置值的方法。
setex
方法:设置带有过期时间的键值对
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 设置键为 'token',值为 '123456',过期时间为 60 秒
r.setex('token', 60, '123456')
在上述代码中,setex
方法的第一个参数是键 'token'
,第二个参数是过期时间(单位为秒),第三个参数是值 '123456'
。这意味着 'token'
这个键值对会在 60 秒后自动过期并从 Redis 中删除。
psetex
方法:设置带有过期时间(以毫秒为单位)的键值对
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 设置键为 'timestamp',值为 '2023 - 10 - 01 12:00:00',过期时间为 1000 毫秒
r.psetex('timestamp', 1000, '2023 - 10 - 01 12:00:00')
这里 psetex
方法与 setex
类似,只是过期时间是以毫秒为单位。
获取值
获取字符串类型值最常用的方法是 get
方法。此外,还有以下相关方法。
mget
方法:批量获取多个键的值
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 设置多个键值对
r.set('name1', 'Alice')
r.set('name2', 'Bob')
# 批量获取多个键的值
names = r.mget(['name1', 'name2'])
for name in names:
print(name.decode('utf - 8'))
在上述代码中,通过 mget
方法一次性获取了 'name1'
和 'name2'
两个键的值,提高了获取多个值的效率。
getrange
方法:获取字符串的子串
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
r.set('message', 'Hello, Redis!')
# 获取从索引 7 开始到末尾的子串
substring = r.getrange('message', 7, -1)
print(substring.decode('utf - 8'))
getrange
方法的第一个参数是键,第二个参数是子串的起始索引(从 0 开始),第三个参数是子串的结束索引(-1 表示到字符串末尾)。这里获取了 'message'
键对应字符串从索引 7 开始到末尾的子串。
对字符串进行增减操作
如果字符串的值是数字类型,redis - py
还提供了对其进行增减操作的方法。
incr
方法:将键对应的值增加 1
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 设置键为 'counter',初始值为 10
r.set('counter', 10)
# 将 'counter' 的值增加 1
r.incr('counter')
# 获取 'counter' 的值
new_counter = r.get('counter')
print(int(new_counter))
incrby
方法:将键对应的值增加指定的整数
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
r.set('score', 50)
# 将'score' 的值增加 20
r.incrby('score', 20)
# 获取'score' 的值
new_score = r.get('score')
print(int(new_score))
decr
方法:将键对应的值减少 1
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
r.set('stock', 100)
# 将'stock' 的值减少 1
r.decr('stock')
# 获取'stock' 的值
new_stock = r.get('stock')
print(int(new_stock))
decrby
方法:将键对应的值减少指定的整数
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
r.set('quantity', 50)
# 将 'quantity' 的值减少 10
r.decrby('quantity', 10)
# 获取 'quantity' 的值
new_quantity = r.get('quantity')
print(int(new_quantity))
操作哈希类型数据
哈希类型在 Redis 中用于存储字段和值的映射关系,类似于 Python 中的字典。redis - py
提供了很多操作哈希类型数据的方法。
设置哈希字段值
hset
方法:设置单个哈希字段的值
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 设置哈希键为 'user:1',字段为 'name',值为 'Tom'
r.hset('user:1', 'name', 'Tom')
hmset
方法:设置多个哈希字段的值
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
data = {
'name': 'Jerry',
'age': 25,
'email': 'jerry@example.com'
}
# 设置哈希键为 'user:2' 的多个字段值
r.hmset('user:2', data)
在上述代码中,通过 hmset
方法一次性设置了 'user:2'
这个哈希键的多个字段值。
获取哈希字段值
hget
方法:获取单个哈希字段的值
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取哈希键为 'user:1',字段为 'name' 的值
name = r.hget('user:1', 'name')
print(name.decode('utf - 8'))
hmget
方法:获取多个哈希字段的值
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取哈希键为 'user:2' 的 'name' 和 'email' 字段的值
fields = ['name', 'email']
values = r.hmget('user:2', fields)
for value in values:
print(value.decode('utf - 8'))
hgetall
方法:获取哈希键的所有字段和值
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取哈希键为 'user:2' 的所有字段和值
all_data = r.hgetall('user:2')
for key, value in all_data.items():
print(key.decode('utf - 8'), ':', value.decode('utf - 8'))
获取哈希字段数量
可以使用 hlen
方法获取哈希键中字段的数量。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取哈希键为 'user:2' 的字段数量
field_count = r.hlen('user:2')
print(field_count)
判断哈希字段是否存在
使用 hexists
方法可以判断哈希键中某个字段是否存在。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 判断哈希键为 'user:2' 的 'age' 字段是否存在
exists = r.hexists('user:2', 'age')
print(exists)
操作列表类型数据
Redis 中的列表是一个双向链表结构,可以在列表的两端进行插入和删除操作。redis - py
提供了丰富的方法来操作列表类型数据。
在列表两端插入元素
lpush
方法:在列表头部插入元素
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 在列表 'fruits' 的头部插入元素 'apple'
r.lpush('fruits', 'apple')
rpush
方法:在列表尾部插入元素
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 在列表 'fruits' 的尾部插入元素 'banana'
r.rpush('fruits', 'banana')
从列表两端弹出元素
lpop
方法:从列表头部弹出元素
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 从列表 'fruits' 的头部弹出元素
fruit = r.lpop('fruits')
print(fruit.decode('utf - 8'))
rpop
方法:从列表尾部弹出元素
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 从列表 'fruits' 的尾部弹出元素
fruit = r.rpop('fruits')
print(fruit.decode('utf - 8'))
获取列表长度
使用 llen
方法可以获取列表的长度。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取列表 'fruits' 的长度
length = r.llen('fruits')
print(length)
获取列表指定范围的元素
使用 lrange
方法可以获取列表指定范围的元素。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 在列表 'numbers' 中插入多个元素
r.rpush('numbers', 1)
r.rpush('numbers', 2)
r.rpush('numbers', 3)
r.rpush('numbers', 4)
r.rpush('numbers', 5)
# 获取列表 'numbers' 中索引从 1 到 3 的元素
sub_list = r.lrange('numbers', 1, 3)
for number in sub_list:
print(int(number))
在上述代码中,lrange
方法的第一个参数是列表键,第二个参数是起始索引(从 0 开始),第三个参数是结束索引(包含该索引位置的元素)。
操作集合类型数据
Redis 的集合是无序的、唯一的元素集合。redis - py
提供了一系列操作集合类型数据的方法。
添加元素到集合
使用 sadd
方法可以向集合中添加元素。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 向集合 'colors' 中添加元素'red'
r.sadd('colors','red')
从集合中移除元素
使用 srem
方法可以从集合中移除元素。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 从集合 'colors' 中移除元素'red'
r.srem('colors','red')
获取集合中的所有元素
使用 smembers
方法可以获取集合中的所有元素。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取集合 'colors' 中的所有元素
members = r.smembers('colors')
for member in members:
print(member.decode('utf - 8'))
获取集合元素数量
使用 scard
方法可以获取集合中元素的数量。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取集合 'colors' 中元素的数量
count = r.scard('colors')
print(count)
集合间的操作
- 交集:使用
sinter
方法可以获取多个集合的交集。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 向集合'set1' 中添加元素
r.sadd('set1', 1)
r.sadd('set1', 2)
r.sadd('set1', 3)
# 向集合'set2' 中添加元素
r.sadd('set2', 2)
r.sadd('set2', 3)
r.sadd('set2', 4)
# 获取集合'set1' 和'set2' 的交集
intersection = r.sinter('set1','set2')
for value in intersection:
print(int(value))
- 并集:使用
sunion
方法可以获取多个集合的并集。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取集合'set1' 和'set2' 的并集
union = r.sunion('set1','set2')
for value in union:
print(int(value))
- 差集:使用
sdiff
方法可以获取多个集合的差集。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取集合'set1' 与'set2' 的差集
difference = r.sdiff('set1','set2')
for value in difference:
print(int(value))
操作有序集合类型数据
Redis 的有序集合与集合类似,也是唯一元素的集合,但每个元素都会关联一个分数(score),通过分数来对元素进行排序。redis - py
提供了相应的方法来操作有序集合。
添加元素到有序集合
使用 zadd
方法可以向有序集合中添加元素及其分数。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 向有序集合 'ranking' 中添加元素 'Alice',分数为 85
r.zadd('ranking', {'Alice': 85})
获取有序集合中指定范围的元素
- 按分数范围获取:使用
zrangebyscore
方法可以获取有序集合中指定分数范围的元素。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 向有序集合 'ranking' 中添加多个元素及其分数
r.zadd('ranking', {'Alice': 85, 'Bob': 90, 'Charlie': 78})
# 获取分数在 80 到 90 之间的元素
result = r.zrangebyscore('ranking', 80, 90)
for member in result:
print(member.decode('utf - 8'))
- 按索引范围获取:使用
zrange
方法可以获取有序集合中指定索引范围的元素。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取有序集合 'ranking' 中索引从 0 到 1 的元素
result = r.zrange('ranking', 0, 1)
for member in result:
print(member.decode('utf - 8'))
获取有序集合元素数量
使用 zcard
方法可以获取有序集合中元素的数量。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取有序集合 'ranking' 中元素的数量
count = r.zcard('ranking')
print(count)
获取有序集合中元素的分数
使用 zscore
方法可以获取有序集合中某个元素的分数。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 获取有序集合 'ranking' 中 'Alice' 的分数
score = r.zscore('ranking', 'Alice')
print(score)
事务操作
Redis 支持事务,redis - py
也提供了相应的功能来实现事务操作。事务可以将多个命令打包在一起执行,要么所有命令都执行成功,要么都不执行。
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 开启事务
pipe = r.pipeline()
try:
# 在事务中添加命令
pipe.set('key1', 'value1')
pipe.set('key2', 'value2')
# 执行事务
pipe.execute()
except redis.RedisError as e:
print(f"事务执行出错: {e}")
# 可以选择回滚事务,不过 Redis 事务自动回滚
pipe.reset()
在上述代码中:
- 通过
r.pipeline()
开启一个事务管道pipe
。 - 使用
pipe
对象添加需要执行的 Redis 命令,如pipe.set('key1', 'value1')
和pipe.set('key2', 'value2')
。 - 最后通过
pipe.execute()
执行事务中的所有命令。如果在执行过程中出现错误,会捕获redis.RedisError
异常。虽然 Redis 事务会自动回滚,但在 Python 代码中可以根据需要进行相应的处理,比如这里使用pipe.reset()
重置管道。
发布与订阅
Redis 提供了发布订阅功能,redis - py
也支持这一特性。通过发布订阅,客户端可以订阅一个或多个频道,当有消息发布到这些频道时,订阅者会收到相应的消息。
订阅频道
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 创建发布订阅对象
pubsub = r.pubsub()
# 订阅频道 'news'
pubsub.subscribe('news')
# 监听消息
for message in pubsub.listen():
if message['type'] =='message':
print(f"收到消息: {message['data'].decode('utf - 8')}")
在上述代码中:
- 首先通过
r.pubsub()
创建一个发布订阅对象pubsub
。 - 然后使用
pubsub.subscribe('news')
订阅频道'news'
。 - 通过
for message in pubsub.listen()
循环监听频道上发布的消息。当接收到消息时,判断消息类型,如果是'message'
类型,则打印消息内容。
发布消息到频道
import redis
r = redis.Redis(host='localhost', port=6379, db = 0)
# 发布消息到频道 'news'
r.publish('news', '新的新闻报道来了!')
在这个示例中,使用 r.publish('news', '新的新闻报道来了!')
将消息 '新的新闻报道来了!'
发布到频道 'news'
上,订阅了该频道的客户端会收到这条消息。
通过以上对 redis - py
库的详细介绍,你已经掌握了在 Python 中使用 redis - py
连接 Redis 数据库并进行各种数据操作、事务处理以及发布订阅等功能的方法。在实际项目中,可以根据具体需求灵活运用这些知识来充分发挥 Redis 的优势。