下面的代碼迭代List集合。 Server對象只包含描述和URL屬性,並在程序執行開始時填充。從多個後臺更新ListView任務不斷添加相同的ListViewItem
對於List<Server>
中的每個服務器,我開始一個新任務,調用一個名爲GetMonitorData
的函數。 GetMonitorData
只是讀取遠程文件,解析出一些數據,並返回包含解析出的數據的ListViewItem
。最後,在任務完成之後我添加了返回ListViewItem
到ListView
在ContinueWith()
:
foreach (Server server in Servers)
{
Task<ListViewItem> mainTask = Task.Factory.StartNew<ListViewItem>(() =>
{
return GetMonitorData(server);
});
Task contTask = mainTask.ContinueWith(task =>
{
lstServers.Items.Add(task.Result);
}, TaskScheduler.FromCurrentSynchronizationContext());
//System.Threading.Thread.Sleep(500);
}
private ListViewItem GetMonitorData(Server server)
{
XDocument monitorDoc = XDocument.Load(server.MonitorURL);
string version = monitorDoc.Root.Element("version").Value;
ListViewItem lstItem = new ListViewItem(new string[] { server.ClientName, version });
return lstItem;
}
public class Server
{
public string ClientName { get; set; }
public string MonitorURL { get; set; }
}
出於某種原因,雖然我只是繼續得到同樣ListViewItem
回ContinueWith()
,所以我的ListView在同一ListViewItem
的多個副本它。有趣的是,如果我取消對System.Threading.Thread.Sleep(500)
行的註釋(從而使任務有一點時間完成),我將按照預期爲List<Server>
中的每個服務器獲取唯一的ListViewItem
。
我錯過了什麼?
也許'GetMonitorData()'不是線程安全的。你可以發佈'GetMonitorData'的代碼嗎? – 2014-09-28 08:39:02
您的'GetMonitorData'方法是線程安全的嗎? – 2014-09-28 08:40:29
嘗試[lock](http://msdn.microsoft.com/en-us/library/c5kehkcz.aspx)'GetMonitorData()'。 無論如何,沒有人能夠幫助你,如果不顯示更多的代碼 – nicks 2014-09-28 08:55:03