簡體   English   中英

為什么foreach與Parallel.ForEach之間存在這種差異?

[英]Why this difference between foreach vs Parallel.ForEach?

任何人都可以用簡單的語言向我解釋為什么我在使用foreach時獲得大約65 k的文件,而在使用Parallel.ForEach時大於3 GB?

foreach的代碼:

// start node xml document
var logItems = new XElement("log", new XAttribute("start", DateTime.Now.ToString("yyyy-MM-ddTHH:mm:ss")));
var products = new ProductLogic().SelectProducts();
var productGroupLogic = new ProductGroupLogic();
var productOptionLogic = new ProductOptionLogic();
// loop through all products
foreach (var product in products)
{
    // is in a specific group
    var id = Convert.ToInt32(product["ProductID"]);
    var isInGroup = productGroupLogic.GetProductGroups(new int[] { id }.ToList(), groupId).Count > 0;
    // get product stock per option
    var productSizes = productOptionLogic.GetProductStockByProductId(id).ToList();
    // any stock available
    var stock = productSizes.Sum(ps => ps.Stock);
    var hasStock = stock > 0;
    // get webpage for this product
    var productUrl = string.Format(url, id);
    var htmlPage = Html.Page.GetWebPage(productUrl);
    // check if there is anything to log
    var addToLog = false;
    XElement sizeElements = null;
    // if has no stock or in group
    if (!hasStock || isInGroupNew)
    {
        // page shows => not ok => LOG!
        if (!htmlPage.NotFound) addToLog = true;
    }
    // if page is ok
    if (htmlPage.IsOk)
    {
        sizeElements = GetSizeElements(htmlPage.Html, productSizes);
        addToLog = sizeElements != null;
    }
    if (addToLog) logItems.Add(CreateElement(productUrl, htmlPage, stock, isInGroup, sizeElements));
}
// save
var xDocument = new XDocument(new XDeclaration("1.0", "utf-8", "yes"), new XElement("log", logItems));
xDocument.Save(fileName);

使用並行代碼是一個小改動,只需用Parallel.ForEach替換foreach:

// loop through all products
Parallel.ForEach(products, product =>
{
    ... code ...
};

GetSizeElements和CreateElements方法都是靜態的。

update1我使用鎖定方法GetSizeElements和CreateElements線程安全,也沒有幫助。

update2我得到了解決問題的答案。 那太好了。 但我想更多地了解為什么這些代碼創建的文件比foreach解決方案大得多。 我正在嘗試使用線程時代碼如何工作更有意義。 通過這種方式,我可以獲得更多洞察力,並且可以學會避免陷阱。

有一點是突出的:

if (addToLog) 
  logItems.Add(CreateElement(productUrl, htmlPage, stock, isInGroup, sizeElements));

logItems不是logItems 這可能是你的核心問題,但還有很多其他的可能性。

你有輸出文件,尋找差異。

嘗試在foreach循環中定義以下參數。

var productGroupLogic = new ProductGroupLogic();
var productOptionLogic = new ProductOptionLogic();

我認為只有兩個被並行foreach循環中的所有線程使用,結果不必要地增加。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM