对.Net中链接列表的多线程访问

时间:2011-09-21 09:21:52

标签: c# .net collections linked-list

我需要一个链表才能在双方添加项目。该列表将保存要在趋势查看器中显示的数据。由于我需要在完全读取数据之前显示大量数据,所以我想要做的是读取我已经写过的数据块,而当我读到该块有两个线程填充两侧集合:

enter image description here

我想过使用LinkedList,但它表示不支持这种情况。在框架中有什么想法可以帮助我或者我是否必须从头开发我的自定义列表?

提前致谢。

编辑:解决方案的主要思想是在没有锁定任何内容的情况下执行此操作,因为我正在读取在其他位置写入时不会更改的列表。我的意思是,读取线程只会读取一个块(从A到B)(已经写入的部分)。当它完成并且其他块已完全写入时,读者将在写入新数据时读取这些块。

请参阅更新的图表:

enter image description here

5 个答案:

答案 0 :(得分:2)

如果您使用的是.NET4,则可以使用两个ConcurrentQueue。一个用于左侧,一个用于右侧。

答案 1 :(得分:1)

您可以使用链接列表,只使用常规的.NET线程结构(如lock关键字)来保护对列表的访问。

无论如何,您开发的任何自定义列表都可能会执行此类操作。

答案 2 :(得分:1)

我建议考虑使用单一数据结构的其他方法来保持数据输入,这样就可以保持数据消息的排序顺序。 例如,您可以使用阻止队列,在此SO帖子中,您可以找到很好的示例Creating a blocking Queue in .NET?

答案 3 :(得分:1)

为什么不使用LinkedList类。 文档说它不是线程安全的,所以你必须自己同步对列表的访问,但你必须对多个线程访问的任何数据结构执行此操作。

性能应该很安静这里是msdn关于在任何位置插入节点的说法:

  

LinkedList提供LinkedListNode类型的单独节点,因此插入和删除是O(1)操作。

您只需使用lock构造锁定读取和插入操作。

修改

好的,我想我明白你想要什么。您需要一个像数据结构这样的列表,它被分成多个项目块。您希望独立编写和读取项目块而不锁定整个列表。

我建议使用LinkedList来保存你的数据项块。 块本身可以表示为简单List或者也可以是LinkedList实例。

您必须锁定对全局LinkedList的访问权限。

现在,您的编写者线程一次填充一个包含n个项目的私有列表。完成后,编写器锁定LinkedList并将其带有dataitems的私有列表添加到LinkedList。

读者线程锁定LinkedList读取一个块并释放锁。现在它可以处理n个数据项而不会锁定它们。

答案 4 :(得分:1)

如果我理解正确,您有一个链接列表,您可以在开始和结束时添加数据。您永远不会在其他地方添加或删除。如果是这种情况,您不必担心线程,因为其他线程永远不会干涉。

简单地做这样的事情:

        //Everything between first and last is thread safe since 
        //the other threads only add before and after.
        LinkedListNode<object> first = myList.First;
        LinkedListNode<object> current = first;
        LinkedListNode<object> last = myList.Last;
        bool done = false;

        if (current == null) return; //empty list
        do
        {
            //do stuff
            if (current == last) done = true;
            current = current.Next;
        } while (!done && current != null);

完成本节后,您可以使用新myList.First到第一个以及从最后一个到新myList.Last的另外两个部分。