c#wpf中函数内的后台工作程序

本文关键字:后台 工作程序 函数 c#wpf | 更新日期: 2023-09-27 18:28:13

我在C#wpf中制作了一个简单的gui,(很抱歉我不能显示gui,因为我的声誉低于10)

它由richtextbox和一些其他控件组成。嗯。。。该应用程序将读取一个文件,然后在使用后台工作程序读取文件时逐行将文件内容显示到richtextbox。读取文件的功能如下:

    public int parse_persoFile2(string fname, BackgroundWorker worker, DoWorkEventArgs e)
    {
        if (fname == null) return -1;
        System.IO.StreamReader ifs;
        ifs = new System.IO.StreamReader(fname);
        int max = (int)e.Argument;
        int p = 0;
        while (ifs.Peek() != -1)
        {
            string tempData = ifs.ReadLine();
            if (tempData.Contains("CMD=5107") || tempData.Contains("CMD=5106") || tempData.Contains("CMD=5102"))
            {
                //field.AppendText(tempData.Remove(tempData.LastIndexOf('''')).Remove(0, 4) + "'r'n");
                //field.AppendText("--------'r'n");
                //System.Threading.Thread.Sleep(500);
                string data = tempData.Remove(tempData.LastIndexOf('''')).Remove(0, 4) + "'r'n";
                worker.ReportProgress(p, data);
            }
            p++;
        }
        worker.ReportProgress(100);
        return 0;
    }

正如我们所看到的,我在这个函数中使用backgroundworker来获取从文件中读取的字符串,然后将该字符串发送到reportprogress,以便在richtextbox中显示。注意,persoFile2函数是由我程序中的另一个对象生成的…:-)

然后,对于其余部分,我已经完成了doWork函数、worker_progressChanged和worker_RunWorkerCompleted,以使backroundWorker正常工作。这些代码是这样的:

    private void doWork(object sender, DoWorkEventArgs e)
    {
        BackgroundWorker wrk = sender as BackgroundWorker;
        parser.parse_persoFile2(fileName, wrk, e);
    }
    private void proggChanged(object sender, ProgressChangedEventArgs e)
    {
        if(e.UserState != null)
        mRTB.AppendText(e.UserState.ToString());
    }
    private void completed(object sender, RunWorkerCompletedEventArgs e)
    {
        MessageBox.Show("Ok....");
    }

嗯。。。。当我运行这个程序时,我的richtextbox似乎没有从文件中逐行打印字符串,但它在最后只打印一次…:-3.不,这才是我真正的问题。我读过这篇文章http://msdn.microsoft.com/en-us/library/system.componentmodel.backgroundworker.aspx,但仍然不知道……:3

c#wpf中函数内的后台工作程序

如果调用ReportProgress方法过快,UI线程可能在BackgroundWorker再次调用之前没有机会处理"进度"并进行适当更新。

private void doWork(object sender, DoWorkEventArgs e)
{
    var wrk = sender as BackgroundWorker;
    // obviously you wouldn't really do this :)
    while(true)
        wrk.ReportProgress(0);
}

为了看到你期待的效果,你可以在DoWork事件中设置一个人为的"暂停",以便给UI时间进行适当的更新:

private void doWork(object sender, DoWorkEventArgs e)
{
    var wrk = sender as BackgroundWorker;
    var p = 0;
    while(true)
    {
        wrk.ReportProgress(p++);
        Thread.Sleep(100);
    }
}

至于您的情况,如果代码执行得那么快,您实际上可能不需要在单独的线程中执行它。

或者,你可以更新你的UI说"请等待。正在加载…",然后在BackgroundWorker中完成你需要做的一切,并在最后将最终结果返回到UI。