线程锁允许同时线程访问
Thread lock allows simultaneous thread access
我有一个助手 class,我的 web 应用程序的多个同时用户会经常调用它。此 class 中的一个函数尝试创建一个在数据库中保证唯一的字符串,即使有 50 个不同的 users/threads 同时调用该函数。以下是我的代码的基本部分:
private Object threadLock = new Object();
private string generateConfigIDThreadLock(Settings settings, string salesOrderNumber, string configModifiedOn) {
lock(threadLock) {
return generateConfigID(settings, salesOrderNumber, configModifiedOn);
}
}
private string generateConfigID(Settings settings, string salesOrderNumber, string configModifiedOn) {
string soTruncated = string.Empty;
if (salesOrderNumber.Length >= 5) {
soTruncated = salesOrderNumber.Substring(salesOrderNumber.Length - 5, 5);
} else {
soTruncated = salesOrderNumber;
}
int configModifiedOnSummed = Utilities.SumNumbers(configModifiedOn);
string newConfigID = $ "{soTruncated}-{DateTime.Now.Hour}{DateTime.Now.Minute}{DateTime.Now.Second}{DateTime.Now.Millisecond}-{configModifiedOnSummed}";
System.Threading.Thread.Sleep(50); // simulate the time for an API roundtrip
return newConfigID;
}
在我的测试工具中,我通过这样做来模拟大量同时使用:
static void Main(string[] args) {
int n = 50;
for (int i = 0; i < n; i++) {
Thread t = new Thread(TestOnMultipleThreads);
t.Start();
}
Console.ReadLine();
}
private static void TestOnMultipleThreads() {
var functions = new Functions();
string configID = functions.GetConfigID(string.Empty, "S-00018437", "2021-12-11 22:11:22");
if (configIDs.Contains(configID)) {
Console.WriteLine("PROLBEM! ConfigId was generated twice: " + configID);
} else {
Console.WriteLine("Unique configID: " + configID);
configIDs.Add(configID);
}
}
我无法使用 guid 来实现唯一性;我需要将字符串保持在 25 个字符以下,并在配置 ID 中使用部分 SO # 和时间戳。注意 TestOnMultipleThreads()
中的硬编码销售订单号和 date/time 戳记;这是一个真实的场景。许多呼叫者可能具有相同的 SO # 和相同的日期时间。我需要使用销售订单 # 的元素和当前时间戳来生成唯一性。如您所见,milsecs
是我唯一字符串的一部分,因此即使 2 次调用相隔 1 毫秒,生成的字符串 ID 也将是唯一的。但是在我的模拟中,我每次都会得到重复项。这似乎意味着我的线程锁不起作用;如果是的话,并且由于我也在使用 Thread.Sleep(50)
,因此不可能在相同的 1 毫秒内生成配置 ID。
我做错了什么?为什么我得到重复项?为什么线程阻塞没有按预期发生?
在您的代码中,看起来每个线程都在处理一个单独的 Functions 实例,因此它们每个都锁定在自己的(单独的)锁定对象上。
快速解决方法是将该对象设为静态,以便它在所有 Functions 实例之间共享,或者让所有线程共享同一个 Functions 实例。
我有一个助手 class,我的 web 应用程序的多个同时用户会经常调用它。此 class 中的一个函数尝试创建一个在数据库中保证唯一的字符串,即使有 50 个不同的 users/threads 同时调用该函数。以下是我的代码的基本部分:
private Object threadLock = new Object();
private string generateConfigIDThreadLock(Settings settings, string salesOrderNumber, string configModifiedOn) {
lock(threadLock) {
return generateConfigID(settings, salesOrderNumber, configModifiedOn);
}
}
private string generateConfigID(Settings settings, string salesOrderNumber, string configModifiedOn) {
string soTruncated = string.Empty;
if (salesOrderNumber.Length >= 5) {
soTruncated = salesOrderNumber.Substring(salesOrderNumber.Length - 5, 5);
} else {
soTruncated = salesOrderNumber;
}
int configModifiedOnSummed = Utilities.SumNumbers(configModifiedOn);
string newConfigID = $ "{soTruncated}-{DateTime.Now.Hour}{DateTime.Now.Minute}{DateTime.Now.Second}{DateTime.Now.Millisecond}-{configModifiedOnSummed}";
System.Threading.Thread.Sleep(50); // simulate the time for an API roundtrip
return newConfigID;
}
在我的测试工具中,我通过这样做来模拟大量同时使用:
static void Main(string[] args) {
int n = 50;
for (int i = 0; i < n; i++) {
Thread t = new Thread(TestOnMultipleThreads);
t.Start();
}
Console.ReadLine();
}
private static void TestOnMultipleThreads() {
var functions = new Functions();
string configID = functions.GetConfigID(string.Empty, "S-00018437", "2021-12-11 22:11:22");
if (configIDs.Contains(configID)) {
Console.WriteLine("PROLBEM! ConfigId was generated twice: " + configID);
} else {
Console.WriteLine("Unique configID: " + configID);
configIDs.Add(configID);
}
}
我无法使用 guid 来实现唯一性;我需要将字符串保持在 25 个字符以下,并在配置 ID 中使用部分 SO # 和时间戳。注意 TestOnMultipleThreads()
中的硬编码销售订单号和 date/time 戳记;这是一个真实的场景。许多呼叫者可能具有相同的 SO # 和相同的日期时间。我需要使用销售订单 # 的元素和当前时间戳来生成唯一性。如您所见,milsecs
是我唯一字符串的一部分,因此即使 2 次调用相隔 1 毫秒,生成的字符串 ID 也将是唯一的。但是在我的模拟中,我每次都会得到重复项。这似乎意味着我的线程锁不起作用;如果是的话,并且由于我也在使用 Thread.Sleep(50)
,因此不可能在相同的 1 毫秒内生成配置 ID。
我做错了什么?为什么我得到重复项?为什么线程阻塞没有按预期发生?
在您的代码中,看起来每个线程都在处理一个单独的 Functions 实例,因此它们每个都锁定在自己的(单独的)锁定对象上。
快速解决方法是将该对象设为静态,以便它在所有 Functions 实例之间共享,或者让所有线程共享同一个 Functions 实例。