[英]C# - How to change value of a progress bar in a secondary thread
In my program I import millions of records to a SQL Server database with the help of SqlBulkCopy class. 在我的程序中,借助于SqlBulkCopy类,将数百万条记录导入到SQL Server数据库中。 Since this is a heavy lifting it takes quite some time.
由于这是一项繁重的工作,因此需要相当长的时间。 While the process goes on I want to show the progress in a progressbar control.
当过程继续进行时,我想在进度条控件中显示进度。 To be notified for the rows copied I've done this:
要通知复制的行,我这样做:
.......
bulkCopy.NotifyAfter = 2000;
bulkCopy.SqlRowsCopied += new SqlRowsCopiedEventHandler(bulkCopy_SqlRowsCopied);
.......
Now in the bulkCopy_SqlRowsCopied method I want to change the value of the progress bar. 现在,在bulkCopy_SqlRowsCopied方法中,我想更改进度栏的值。 But I think I need to make it on a seperate thread.
但是我认为我需要在单独的线程上创建它。 How can I do this?
我怎样才能做到这一点?
You can have one extension class, like 您可以拥有一个扩展类,例如
public static class ControlExtensions
{
public static void Invoke(this Control control, Action action)
{
if (control.InvokeRequired) control.Invoke(new MethodInvoker(action), null);
else action.Invoke();
}
}
Now when ever and where ever you want to update status of progress bar, you can do 现在,无论何时何地您想要更新进度条的状态,您都可以
progressBar.Invoke(() => { progressBar.PerformStep(); };
Hope this works for you. 希望这对您有用。
You could execute your copy in a BackgroundWorker and use ReportProgress
to update your progressbar... 您可以在BackgroundWorker中执行您的副本,并使用
ReportProgress
更新进度条...
You can find an example at http://msdn.microsoft.com/en-us/library/cc221403(v=vs.95).aspx . 您可以在http://msdn.microsoft.com/zh-cn/library/cc221403(v=vs.95).aspx中找到示例。
The use of a BackgroundWorker
for time-consuming operations is good because your UI (with the main thread) is free to be updated/refreshed, making user experience better. 使用
BackgroundWorker
进行耗时的操作很好,因为您的UI(带有主线程)可以自由更新/刷新,从而使用户体验更好。
For non-collection properties WPF will marshall the value on to the UI thread for you. 对于非集合属性,WPF将为您将值编组到UI线程上。 So if you have a ViewModel with a progress property that raises the PropertyChanged event you can bind your ProgressBar to the ProgressBar.
因此,如果您的ViewModel带有一个引发PropertyChanged事件的progress属性,则可以将ProgressBar绑定到ProgressBar。
For this to work, your ViewModel instance should not be a DependencyObject (but that is a bad idea for so many reasons). 为此,您的ViewModel实例不应是DependencyObject(但这是个坏主意,原因有很多)。 This way you can reference it from your background thread and set the Progress property.
这样,您可以从后台线程引用它并设置Progress属性。
Using the Invoke() Method of the ProgressBar Control in your EventHandler "bulkCopy_SqlRowsCopied", make sure you set the NotifyAfter property of the SqlBulkCopy class to an amount that would reflect some form of percentage. 在EventHandler“ bulkCopy_SqlRowsCopied”中使用ProgressBar控件的Invoke()方法,确保将SqlBulkCopy类的NotifyAfter属性设置为可以反映某种百分比形式的数量。
Now in the bulkCopy_SqlRowsCopied method I want to change the value of the progress bar.
现在,在bulkCopy_SqlRowsCopied方法中,我想更改进度栏的值。 But I think I need to make it on a seperate thread.
但是我认为我需要在单独的线程上创建它。 How can I do this?
我怎样才能做到这一点?
If you are using .Net 4.0 you could start your bulk copy in a Task, other versions you could use the ThreadPool, create your own thread 如果您使用的是.Net 4.0,则可以在Task中启动批量复制,其他版本则可以使用ThreadPool,创建自己的线程
Task.Factory.StartNew(MyBulkCopyMethod);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.