0

我有很长时间开发 .net Web 应用程序的经验,但今天我被要求创建一个 Windows 窗体应用程序来根据数据库中的一些数据创建 excel,而我不是 Windows 窗体专家。

它的完成和工作。我使用后台工作人员添加了一个进度条,以便程序可以继续响应,现在我想根据其 OrderId 更改该行的 bgcolor。

我添加了以下内容:

backgroundColor = backgroundColor == Color.White ? Color.WhiteSmoke : Color.White;

这行代码就在我的订单下方,我的订单可能有很多付款等等,所以它就像 Excel 上的很多行只针对一个订单。

如果没有 BackgroundWorker,一切都会像我预期的那样工作,但是,添加它会弄乱一切,因为它在线程中会发生一些奇怪的事情。

我希望我把自己说得很清楚,也希望能找到这个“问题”的答案。

下面是 backgroundworker 的代码,在这个 CreateExcel 方法中有一个 foreach 订单,但是 backgroundworker 是线程化的,我为每个不同订单着色 bgcolor 的逻辑不起作用......

private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
{
    Util.CreateExcel(_orders, _fileName, sender as BackgroundWorker, e);
}

我尝试发布一些图片,但我需要更多的声誉。

所需的结果类似于“斑马”,每个订单都有不同的 bgcolor。没有 backgroudworker 这工作正常,但结果很奇怪,有些订单的 bgcolor 与其他订单相同,有些订单很好。

4

1 回答 1

0

您可能在颜色切换代码中有竞争条件:

backgroundColor = backgroundColor == Color.White ? Color.WhiteSmoke : Color.White;

此代码类似于:

if( backgroundColor == Color.White )
      backgroundColor = Color.WhiteSmoke;
else
      backgroundColor = Color.White;

两个或更多线程可能同时遍历IF 代码及其条件,因此您可能有两个线程在完全相同的时间测试并意识到背景现在是白色,这将产生两个 WhiteSmoke 行。

解决这个问题的方法是只允许一个线程通过锁定共享对象(例如在字段中)来独占地执行此块:

lock(syncLock)
{
    backgroundColor = backgroundColor == Color.White ? Color.WhiteSmoke : Color.White;
}
于 2013-08-30T17:04:55.630 回答