using System;
using System.Collections.Generic;
using System.Threading;
using System.Threading.Tasks;
using StackExchange.Redis;
namespace ConAppRedis
{
class Program
{
static void Main(string[] args)
{
ConnectionMultiplexer redis = ConnectionMultiplexer.Connect("localhost,allowAdmin=true");
redis.GetServer("localhost", 6379).FlushAllDatabases();
var are = new AutoResetEvent(false);
const int count = 10000;
RedisKey key = "key";
var t1 = Task.Run(() =>
{
IDatabase db = redis.GetDatabase();
var list = new List<string>();
are.WaitOne();
for (int i = 0; i < count; i++)
{
list.Add(db.ListRightPop(key));
}
});
var t2 = Task.Run(() =>
{
IDatabase db = redis.GetDatabase();
var s = new string('a', 25); // 50 bytes
for (int i = 0; i < count * 2; i++)
{
db.ListLeftPush(key, s);
if (i == count)
{
are.Set();
}
}
Console.WriteLine(db.ListLength(key));
});
Task.WaitAll(t1, t2);
}
}
}
Redis 中的所有操作都是原子的。
据我所知,Redis 中没有版本控制。
因此,将出现阻塞:当一个客户端读取数据时,第二个客户端将等待。
引用:
如果我们在谈论列表- 列表,那么列表的总大小不会影响客户端的工作:一个客户端将数据写入列表,另一个客户端读取。正如我之前所说,其中一个客户端必须等待另一个客户端的操作完成。但是列表的总大小不会影响这一点,因为另一个客户端一次会读取一个 50 字节的短字符串,而不是一次读取列表的全部内容。
我试图用以下 C# 代码来说明这一点:
启动(客户端的)两个任务:第一个首先等待权限启动(它将由第二个任务发出,已写入一半数据),然后开始读取数据。
第二个任务将数据写入列表。最后,此任务获取列表的当前大小并将其打印出来。每次取值都不一样,很自然,大概在 10055 左右。
也就是说,当第二个任务完成写入 20,000 个值时,第一个任务已经读取了将近一半。因此,他们共同依次访问服务器。
但是如果我们谈论使用 APPEND 连接一个字符串,这会导致它的增加,那么第二个任务将等待相当长的时间,以便第一个任务一次完全接收它(否则没有办法)。