异步任务.运行不起作用
本文关键字:不起作用 运行 任务 异步 | 更新日期: 2023-09-27 18:35:48
我只是在下面写了代码,我希望在 C# 中有 3 个具有异步功能的文本文件,但我什么也没看到:
private async void Form1_Load(object sender, EventArgs e)
{
Task<int> file1 = test();
Task<int> file2 = test();
Task<int> file3 = test();
int output1 = await file1;
int output2 = await file2;
int output3 = await file3;
}
async Task<int> test()
{
return await Task.Run(() =>
{
string content = "";
for (int i = 0; i < 100000; i++)
{
content += i.ToString();
}
System.IO.File.WriteAllText(string.Format(@"c:'test'{0}.txt", new Random().Next(1, 5000)), content);
return 1;
});
}
有几个潜在的问题:
c:'test'
存在吗?否则,您将收到错误。- 如前所述,您的
Random
对象可能会生成相同的数字,因为当前系统时间用作种子,并且您几乎同时执行这些操作。您可以通过让他们共享static Random
实例来解决此问题。编辑:但您需要以某种方式同步对它的访问。我在Random
实例上选择了一个简单的lock
,这不是最快的,但适用于此示例。 - 以这种方式构建长
string
效率非常低(例如,对我来说,在调试模式下大约需要 43 秒,一次)。您的任务可能运行良好,并且您没有注意到它实际上正在执行任何操作,因为它需要很长时间才能完成。通过使用StringBuilder
类(例如大约 20 毫秒),它可以做得更快。 - (这不会影响它是否有效,但更像是一种风格上的东西)您不需要在编写的
test()
方法中使用async
和await
关键字。它们是多余的,因为Task.Run
已经返回了一个Task<int>
。
这对我有用:
private async void Form1_Load(object sender, EventArgs e)
{
Task<int> file1 = test();
Task<int> file2 = test();
Task<int> file3 = test();
int output1 = await file1;
int output2 = await file2;
int output3 = await file3;
}
static Random r = new Random();
Task<int> test()
{
return Task.Run(() =>
{
var content = new StringBuilder();
for (int i = 0; i < 100000; i++)
{
content.Append(i);
}
int n;
lock (r) n = r.Next(1, 5000);
System.IO.File.WriteAllText(string.Format(@"c:'test'{0}.txt", n), content.ToString());
return 1;
});
}
每次使用不同的随机数实例将导致随机数生成每次生成相同的数字!
The random number generation starts from a seed value. If the same seed is used repeatedly, the same series of numbers is generated.
这是因为 Random 使用计算机的时间作为种子值,但该值的精度不足以提高计算机的处理速度。
使用相同的随机数生成器,例如:
internal async Task<int> test()
{
return await Task.Run(() =>
{
string content = "";
for (int i = 0; i < 10000; i++)
{
content += i.ToString();
}
System.IO.File.WriteAllText(string.Format(@"c:'test'{0}.txt",MyRandom.Next(1,5000)), content);
return 1;
});
}
编辑:
此外,随机不是线程安全的,因此您应该同步对它的访问:
public static class MyRandom
{
private static Random random = new Random();
public static int Next(int start, int end)
{
lock (random)
{
return random.Next(start,end);
}
}
}