2012-04-03 63 views
-2

这可能吗?将BackgroundWorker传递给由doWork调用的类?

我想要做的是让我的doWork方法实例化另一个类,然后调用它的启动方法。然后我想报告该类的进度回到父类中的ProgressChanged处理程序。我试过传递给BackgroundWorker的引用,但我得到一个错误。

private void ComplianceWorker_DoWork(object sender, DoWorkEventArgs e) 
    { 
     ComplianceControlCenter CCC = 
     new ComplianceControlCenter(taskList.CheckedItems.OfType<string>().ToList(), 
            file_box.Text, &ComplianceWorker); 
     CCC.start(); 
    } 

编辑:

只有1个后台工作。我想通过引用ComplianceControlCenter的构造函数来传递它,以便我可以从该类中向其发送进度更新。推理是这个班做一些相当复杂的工作,我需要有一个分工。如此反复,我想通过从的doWork方法的CCC对象的后台工作,所以我可以调用ComplianceWorker.ReportProgress();

错误1无法获取地址,得到的大小,或指针声明的管理键入('System.ComponentModel.BackgroundWorker')

+3

然后发布错误的详细信息。我想这与'&ComplianceWorker'中的'&'有关,但我想知道。 – 2012-04-03 07:14:50

回答

0

你可以这样做,但我没有看到它为简单情况提供了什么目的。由于已经BackgroundWorker的业务方法中,因此通过创建另一个BackgroundWorker来使用更多线程并没有意义,并且您可以在线执行相同的工作。

如果您仍然想要第二个BackgroundWorker,可以通过将处理程序附加到第二个工作人员的ProgressChanged事件中,将进度更改的事件从第二个工作人员传播到第一个工作人员。然后,该处理程序会在第一个工作人员上提起ProgressChanged事件,传播新闻。

例如:

private void ComplianceWorker_DoWork(object sender, DoWorkEventArgs e) 
{ 
    var CCC = new ComplianceControlCenter(/* ... */); 

    // Assume that CCC exposes a BackgroundWorker, but read below 
    var worker = CCC.Worker; // "second" worker 
    worker.ProgressChanged += this.PropagateProgressChanged; 

    CCC.start(); 
} 

private void PropagateProgressChanged(object sender, ProgressChangedEventArgs e) 
{ 
    var worker = this.worker; // "first" worker 
    worker.ReportProgress(e.ProgressPercentage, e.UserState); 
} 

该代码附加的事件处理程序的 “第二” 工人用

var worker = CCC.Worker; // "second" worker 
worker.ProgressChanged += this.PropagateProgressChanged; 

其中假定ComplianceControlCenter公开其自己的直接BackgroundWorker。由于情况可能并非如此,因此您可以通过将this.PropagateProgressChanged的引用传递给构造函数并让它为您附加事件处理函数来关联该关系。

+0

我只想要1个后台工作者。 – 2012-04-03 16:35:30

0

如果两个后台工作者都相同,则会运行到无限循环。可能会创建两个不同的背景工作者。如果你需要在它们之间有类似的东西,创建一个基类/接口。

+0

我认为OP只是想传递一个参考。 – 2012-04-03 07:16:00

0

为什么不只是将BackgroundWorker的参考作为参数传递给“工作”方法?

编辑:

事实上,你所要做的,如果你想报告进展情况或检查CancellationPending标志,如果你也能想手动取消您的操作。

+0

是的,那正是我想要做的。 – 2012-04-03 16:36:03

+1

BackgroundWorker worker =发件人为BackgroundWorker; – Pedro77 2017-01-12 15:15:44

1

在C#中,引用传递这样的:

ComplianceControlCenter CCC = new ComplianceControlCenter(..., ComplianceWorker); 

不喜欢这个

ComplianceControlCenter CCC = new ComplianceControlCenter(..., &ComplianceWorker); 

作为一个侧面说明,这是习惯,让变量和字段以小写字母,所以我会将ComplianceWorker重命名为complianceWorker。请注意,这也提高了语法高亮的StackOverflow:;-)

ComplianceControlCenter ccc = new ComplianceControlCenter(..., complianceWorker); 
0

如果您需要BackgroundWorker本身DoWork事件中只是上溯造型的sender。也许是这样的:

private void ComplianceWorker_DoWork(object sender, DoWorkEventArgs e) 
{ 
    var worker = sender as BackgroundWorker; 
    if(worker == null) 
    { 
     //ToDo: What should happen if MS changes the behavior?? 
    } 

    ComplianceControlCenter CCC = new ComplianceControlCenter(taskList.CheckedItems.OfType<string>().ToList(), file_box.Text, worker); 
    CCC.start(); 
} 
+0

替代建议:'var worker =(BackgroundWorker)sender;'。如果“MS改变行为”,这将确保程序失败并带有InvalidCastException。 – Heinzi 2012-04-03 07:30:47

+0

@Heinzi:是的,你说得对,但我只是想在代码示例中指出这个问题。 – Oliver 2012-04-03 07:49:54

0

通过这样解决了吧..

ComplianceControlCenter CCC = new ComplianceControlCenter(taskList.CheckedItems.OfType<string>().ToList(), file_box.Text,ref complianceWorker); 

以此为构造函数。

public ComplianceControlCenter(List<string> task_list, String exe_location, ref BackgroundWorker complianceWorker)