Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/linq/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
LINQ操作符完全阻塞了吗?_Linq_Concurrency_Task Parallel Library_Parallel Extensions - Fatal编程技术网

LINQ操作符完全阻塞了吗?

LINQ操作符完全阻塞了吗?,linq,concurrency,task-parallel-library,parallel-extensions,Linq,Concurrency,Task Parallel Library,Parallel Extensions,我正在查看VS2010并发分析器的输出,我注意到我在一些LINQ操作符周围得到了一些线程争用。以下是导致争用的语句: m_dictionary.PermutableSubunits.Select(subunit => subunit.Number).ToArray() LINQ操作符是否阻塞?在作为Parallel.ForEach的一部分运行的任务中使用它们时,我应该更加小心吗?它不应该阻塞,但是如果您使用Linq to SQL,那么如果您的查询需要很长时间来执行,则可能需要非常长的时间

我正在查看VS2010并发分析器的输出,我注意到我在一些LINQ操作符周围得到了一些线程争用。以下是导致争用的语句:

m_dictionary.PermutableSubunits.Select(subunit => subunit.Number).ToArray()

LINQ操作符是否阻塞?在作为Parallel.ForEach的一部分运行的任务中使用它们时,我应该更加小心吗?

它不应该阻塞,但是如果您使用Linq to SQL,那么如果您的查询需要很长时间来执行,则可能需要非常长的时间。。。一般来说,在使用多线程处理的任何时候,都应该“更加小心”,或者像他们说的那样:“小心线程!”


然而,如果您有争用问题,那么您应该真正分析您实际在做什么。Linq不是线程安全的,因此如果您正在对可能从另一个线程更改的实体执行读/写操作,那么您应该正确地同步

我假设您询问的是LINQ to对象,因此代码中的Select调用对应于Enumerable.Select(..)

LINQ to Objects运算符本身不会显式阻止执行线程。但是,它们确实分配内存:例如,ToArray操作符将分配越来越大的数组以缓冲结果

而且,内存分配会导致线程阻塞。分配内存时,CLR或操作系统可能需要获取一些锁,以便找到一块可用内存。更重要的是,CLR可能会在您分配内存时决定运行垃圾收集(GC),这可能会导致严重的线程阻塞


如果服务器GC非常适合您的应用程序,您可以尝试打开它,看看吞吐量是否有所提高。此外,您通常可以编写非LINQ代码,该代码执行的内存分配比LINQ到对象查询更少。在您的特定示例中,我相信LINQ to对象将开始将结果生成到一个小数组中,在结果不合适时分配一个更大的数组。您的自定义实现可能能够在一开始就分配适当大小的数组,从而避免大量不必要的分配。

您是指LINQ运算符,我希望它是单线程还是使用线程池的PLINQ运算符?我不确定我是否理解你的问题。我的意思是LINQ操作符(如上面的Select()和ToArray()),而不是PLINQ(注意上面没有.AsParallel())。上面的代码在由Parallel.ForEach方法启动的任务中运行。这就是你想知道的吗?谢谢Igor,你是对的,我正在使用Linq对象,我也在使用服务器GC。我注意到,在重写某些代码时,性能有所提高,这些代码从Linq到普通的for循环都受到了很大的影响,所以我想我暂时还是继续这样做吧。