字非舍予

  博客园 :: 首页 :: 博问 :: 闪存 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理 ::

    最近做了一个本地和远程服务器数据的同步,突发念头尝试了一下窗体程序。因为同步数据操作非常耗时,所以用了BackgroundWorker。网上搜罗了一下,大致用法如下:

      主要的事件及参数。
          1、DoWork——当执行BackgroundWorker.RunWorkerAsync方法时会触发该事件,并且传递DoWorkEventArgs参数;
          2、ProgressChanged——操作处理中获得的处理状态变化,通过BackgroundWorker.ReportProgress(int)方法触发该事件,并且传递ProgressChangedEventArgs,其中包含了处理的百分比;
          3、RunWorkerCompleted——异步操作完成后会触发该事件,当然如果需要在操作过程中结束可以执行BackgroundWorker.CancelAsync方法要求异步调用中止,并且在异步委托操作中检测BackgroundWorker.CancellationPending属性如果为true的话,跳出异步调用,同时将DoWorkEventArgs.Cancel属性设为true,这样当退出异步调用的时候,可以让处理RunWorkerCompleted事件的函数知道是正常退出还是中途退出。

      主要的方法。

          1、BackgroundWorker.RunWorkerAsync——“起动”异步调用的方法,有两次重载RunWorkerAsync(),RunWorkerAsync(object argument),后者提供了一个参数以供异步调用使用。

          2、BackgroundWorker.ReportProgress——有时候需要在一个冗长的操作中向用户不断反馈进度,这样的话就可以调用的ReportProgress(int percent),在调用 ReportProgress 方法时,触发ProgressChanged事件。提供一个在 0 到 100 之间的整数,它表示后台活动已完成的百分比。你也可能提供任何对象作为第二个参数,允许你 给事件处理程序传递状态信息。作为传递到此过程的 ProgressChangedEventArgs 参数属性,百分比和你自己的对象(如果提供的话)均要被传递到 ProgressChanged 事件处理程序。这些属性被分别命名为 ProgressPercentage 和 UserState,并且你的事件处理程序可以以任何需要的方式使用它们。(注意:只有在BackgroundWorker.WorkerReportsProgress属性被设置为true该方法才可用)。

          3、BackgroundWorker.CancelAsync——但需要退出异步调用的时候,就调用的这个方法。但是样还不够,因为它仅仅是将BackgroudWorker.CancellationPending属性设置为true。你需要在具体的异步调用处理的时候,不断检查BackgroudWorker.CancellationPending是否为true,如果是真的话就退出。(注意:只有在BackgroundWorker.WorkerSupportsCancellation属性被设置为true该方法才可用)。

     代码如下:

 

代码
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Data.SqlClient;



namespace mobeyForm
{

    
public partial class Form1 : Form
    {
        
private System.ComponentModel.BackgroundWorker backgroundWorker;

        
public Form1()
        {
            InitializeComponent();
            
//定义线程开始
            backgroundWorker = new BackgroundWorker();
            backgroundWorker.WorkerReportsProgress 
= true;
            backgroundWorker.WorkerSupportsCancellation 
= true;
            backgroundWorker.DoWork 
+= new DoWorkEventHandler(backgroundCalculator_DoWork);
            backgroundWorker.ProgressChanged 
+= new ProgressChangedEventHandler(backgroundCalculator_ProgressChanged);
            backgroundWorker.RunWorkerCompleted 
+= new RunWorkerCompletedEventHandler(backgroundCalculator_RunWorkerCompleted);
            updateStatus(String.Empty);
            updateResult(String.Empty);
        }



        
private void button1_Click(object sender, EventArgs e)
        {
            
this.button1.Enabled = false;
            
this.btnClose.Enabled = false;
            
this.progressBar1.Value = 0;
            
//将调用DoWork事件
            updateStatus("程序执行中,请等待……");

            backgroundWorker.RunWorkerAsync(chkStock.Checked);
        }
        
/// <summary>
        
/// 线程 启动
        
/// </summary>
        
/// <param name="sender"></param>
        
/// <param name="e"></param>
        private void backgroundCalculator_DoWork(object sender, DoWorkEventArgs e)
        {
            
bool updateStock = (bool)e.Argument;//是否更新库存

            
string reslut = string.Empty;
            
//string reslut = new Components.DataUpdate().updateDataTable();
            long successCount = 0;
            
long uploaded = 0;
            
// string websql = "select as_Id,as_ContactMan from C_Address"; 
            string websql = "select ProductId,SKU,CostPrice from Hishop_Products";
            
if (updateStock)
                websql 
= "select ProductId,SKU,CostPrice,Stock from Hishop_Products";
            SqlConnection serverConn 
= null;
            
try
            {
                serverConn 
= new SqlConnection(Components.Const.ServerConnStr);
            }
            
catch (Exception ex)
            {
                reslut 
= string.Format("【请求服务器链接】过程中发生异常已被取消,错误信息:“{0}”", ex.Message);
                e.Result 
= reslut;
                
// e.Cancel = true;
                return;
                
//日志
            }
            DataSet serverDS 
= new DataSet();
            DataTable serverDT 
= new DataTable();
            SqlDataAdapter serverAD 
= new SqlDataAdapter(websql, serverConn);
            SqlCommandBuilder cmb 
= new SqlCommandBuilder(serverAD);//
            serverAD.Fill(serverDS, "Hishop_Products");
            serverDT 
= serverDS.Tables[0];
            
//serverDt= new Components.DataUpdate().getData(websql, Components.Const.ServerConnStr);

            backgroundWorker.ReportProgress(
30);//回发进度

            
if (serverDT != null)
            {
                
if (serverDT.Rows.Count > 0)
                {
                    
try
                    {
                        
for (int i = 0; i < serverDT.Rows.Count; i++)
                        {
                            
string SKU = serverDT.Rows[i]["SKU"].ToString();
                            
// string sql  ="select top 1 as_ContactMan from C_Address where  as_Id=" + id;
                            string sql = string.Format("select top 1 Qty,Price from GoodsStocks left join ptype on PtypeId=typeId where UserCode='{0}'", SKU);
                            
try
                            {
                                DataTable locDt 
= new Components.DataUpdate().getData(sql, Components.Const.LocalConnStr);
                                
if (locDt.Rows.Count > 0)
                                {
                                    
string stock = string.Empty;
                                    
if (updateStock)
                                        stock 
= locDt.Rows[0]["Qty"].ToString().Trim();
                                    
string price = locDt.Rows[0]["Price"].ToString().Trim();
                                    
if (stock.Length > 0 && price.Length > 0)
                                    {
                                        
if (updateStock)
                                        {
                                            
int istock = 0;
                                            serverDT.Rows[i][
"Stock"= Int32.TryParse(stock, out istock) == true ? Convert.ToInt32(stock) : Convert.ToInt32(Convert.ToDouble(stock));
                                        }
                                        serverDT.Rows[i][
"CostPrice"= Convert.ToDecimal(price);
                                    }
                                }
                                successCount 
+= 1;
                            }
                            
catch (Exception ex)
                            {
                                
throw new Exception(ex.Message);

                                
//日志
                            }
                        }
                    }
                    
catch (Exception ex)
                    {
                        
//e.Cancel = true;
                        reslut = string.Format("【更新数据】过程中发生异常已被取消,错误信息:“{0}”", ex.Message);
                        e.Result 
= reslut;

                        
return;
                        
//日志
                    }
                    backgroundWorker.ReportProgress(
70);//回发进度

                    
#region 更新到服务器
                    
try
                    {
                        uploaded 
= serverAD.Update(serverDS, "Hishop_Products");
                        serverDS.AcceptChanges();
                    }
                    
catch (Exception ex)
                    {
                        
// e.Cancel = true;
                        reslut = string.Format("【数据更新到服务器】过程中发生异常已被取消,错误信息:“{0}”", ex.Message);
                        e.Result 
= reslut;

                        
return;
                        
//日志
                    }
                    
#endregion

                }

            }
            reslut 
= string.Format("成功更新数目:{0},发生更改项:{1}", successCount, uploaded);
            e.Result 
= reslut;
        }

        
/// <summary>
        
/// 线程 完成
        
/// </summary>
        
/// <param name="sender"></param>
        
/// <param name="e"></param>
        private void backgroundCalculator_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        {
            
if (e.Cancelled)
            {
                
// updateResult("程序被取消");
                updateResult(e.Result.ToString());
                updateStatus(
"程序执行被取消");
            }
            
else
            {
                updateResult(e.Result.ToString());
                updateStatus(
"");
            }

            
this.button1.Enabled = true;
            
this.btnClose.Enabled = true;
            
this.progressBar1.Value = 100;
        }
        
/// <summary>
        
/// 线程 取消
        
/// </summary>
        
/// <param name="sender"></param>
        
/// <param name="e"></param>
        private void OnCancel(object sender, EventArgs e)
        {
            backgroundWorker.CancelAsync();
        }
        
/// <summary>
        
/// 操作处理中获得的处理状态变化
        
/// </summary>
        
/// <param name="sender"></param>
        
/// <param name="e"></param>
        private void backgroundCalculator_ProgressChanged(object sender, ProgressChangedEventArgs e)
        {
            
this.progressBar1.Value = e.ProgressPercentage;
        }
        
/// <summary>
        
/// 界面提示信息提示
        
/// </summary>
        
/// <param name="status"></param>
        private void updateStatus(string status)
        {
            
this.calcStatus.Text = status;
        }
        
/// <summary>
        
/// 运行结果提示
        
/// </summary>
        
/// <param name="result"></param>
        private void updateResult(string result)
        {
            
this.label1.Text = result;
        }

        
private void btnClose_Click(object sender, EventArgs e)
        {
            
this.Close();
            
this.Dispose();
        }
    }
}

 

 

posted on 2010-10-11 16:52  lasi  阅读(520)  评论(0编辑  收藏  举报