如何防止使用相同变量的线程 [英] How to prevent threads using the same variables

查看:59
本文介绍了如何防止使用相同变量的线程的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个多行文本框,我想用多线程处理每一行.

I have a multi-line textbox and I want to process each line with multi threads.

该文本框可能有很多行(超过1000行),但没有那么多线程.我想使用自定义数量的线程来读取所有1000条以上的行,而没有任何重复(就像在每个线程中仅读取UNIQUE行一样,如果其他线程已读取一行,则不要再次读取该行).

The textbox could have a lot of lines (1000+), but not as many threads. I want to use custom amount of threads to read all those 1000+ lines without any duplicates (as in each thread reading UNIQUE lines only, if a line has been read by other thread, not to read it again).

我现在所拥有的:

private void button5_Click(object sender, EventArgs e)
{
    for (int i = 0; i < threadCount; i++)
    {
        new Thread(new ThreadStart(threadJob)).Start();
    }
}

private void threadJob()
{
    for (int i = 0; i < txtSearchTerms.Lines.Length; i++)
    {
        lock (threadLock)
        {
            Console.WriteLine(txtSearchTerms.Lines[i]);
        }
    }
}

它确实启动了正确数量的线程,但是它们都多次读取相同的变量.

It does start the correct amount of threads, but they all read the same variable multiple times.

推荐答案

单独的数据收集和数据处理以及计算后的下一个可能步骤.您可以使用ConcurrentBag<T>安全地收集并行计算的结果,这只是线程安全的收集.
这样一来,您就不必担心锁定"对象,并且所有行都只会被处理"一次.
1.收集数据
2.并行执行收集的数据
3.处理计算结果

Separate data collection and data processing and next possible steps after calculation. You can safely collect results calculated in parallel by using ConcurrentBag<T>, which is simply thread-safe collection.
Then you don't need to worry about "locking" objects and all lines will be "processed" only once.
1. Collect data
2. Execute collected data in parallel
3. Handle calculated result

private string Process(string line)
{
    // Your logic for given line
}

private void Button_Click(object sender, EventArgs e)
{
    var results = new ConcurrentBag<string>();

    Parallel.ForEach(txtSearchTerms.Lines,
                     line =>
                     {
                         var result = Process(line);
                         results.Add(result);
                     });

    foreach (var result in results)
    {
        Console.WriteLine(result);
    }
}  

默认情况下,Parallel.ForEach将使用与基础调度程序提供的线程一样多的线程.

By default Parallel.ForEach will use as much threads as underlying scheduler provides.

您可以通过将ParallelOptions的实例传递给Parallel.ForEach方法来控制已使用线程的数量.

You can control amount of used threads by passing instance of ParallelOptions to the Parallel.ForEach method.

var options = new ParallelOptions
{
    MaxDegreeOfParallelism = Environment.ProcessorCount
};
var results = new ConcurrentBag<string>();
Parallel.ForEach(values,
                 options,
                 value =>
                 {
                     var result = Process(value);
                     results.Add(result);
                 });

这篇关于如何防止使用相同变量的线程的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆