none
关于C#多线程运行先后的问题 RRS feed

  • 问题

  • using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Linq;
    using System.Text;
    using System.Windows.Forms;
    using System.Threading;

    namespace StartThread
    {
        public partial class Form1 : Form
        {
            public Form1()
            {
                InitializeComponent();
            }

            public delegate void mydelegate();
            private void button1_Click(object sender, EventArgs e)
            {
          
                Thread nonParameterThread = new Thread(new ThreadStart(NonParameterRun));
                nonParameterThread.IsBackground = true;
                nonParameterThread.Start();
                this.Invalidate();
               
                    for (int z = 0; z < 312312321; z++)
                    {
                    int j = 2;
                    int i = 1;
                    int k;
                    k = j / i;
                    }
               
             


            }

            public void text()
            {
                label1.Text="Hello,I'm come in";
               
            }

            private void NonParameterRun()
            {
              
                button1.BeginInvoke(new mydelegate(text));
                        
            }
        }
    }

    各位,我想请教个问题,为什么代码执行的时候,我新开了个进程,用来运行label1.Text="Hello,I'm come in“这句话,但是程序没有立刻进行,感觉是运行完了个for循环才会执行label1.Text="Hello,I'm come in“这句代码。

    2011年12月30日 2:55

答案

  • Thread nonParameterThread = new Thread(new ThreadStart(NonParameterRun));//创建线程
    nonParameterThread.IsBackground = true;//后台线程,可以随主线程退出时退出
    nonParameterThread.Start();//开启线程①->
    this.Invalidate();//使整个窗体无效,在稍后的消息循环中,会由系统插入一个WM_PAINT并调用绘制窗体方法。
    
    //一个循环用于占用时间,同时,也让函数结束的时间延长了
    for (int z = 0; z < 312312321; z++)
    {
        int j = 2;
        int i = 1;
        int k;
        k = j / i;
    }
    //windows是一个消息驱动的操作系统
    //建议你看看c++的标准写法,main->registclass->createwindow->messageloop<--循环的处理消息-->
    //.net当然也只是对这个处理封装了,一个ui,实际状态是不停的在响应自己的消息并调用各种的消息处理函数
    //为什么你没看到?因为有很多的OnXXX的方法,例如OnPaint是在收到WM_PAINT时调用的,OnPaint中检查Paint事件
    //是否注册,如果注册过,则调用事件的响应函数。 
    //我没有扯远,下面是解答你问题的
    //接下来呢,事件响应函数执行完毕返回,OnPaint执行完毕返回,才能再次的执行消息循环,对余下的消息进行处理
    //你这里呢?你的线程通过PostMessage的方式改变界面,于是你的界面更新也就间接的排在消息队列中了,反过来,
    //既然要等待消息循环来执行,更新界面,那你的button1_click函数没执行完,button1.OnClick消息响应函数就没
    //完成,就不会处理消息,就不会更新界面。
    //所以,多线程在ui的目的就是将占用界面响应时间长的代码移到另外的线程已保证界面线程可以更快的响应消息
    //不知道我说明白没有
    



    2011 c# mvp China. *George读起来像不像“饺子”?我爱吃饺子,我叫George。
    • 已标记为答案 klvchen 2011年12月30日 9:18
    2011年12月30日 4:34
    版主
  • 呼,看来我白写了。你没看懂,呵呵。最好还是仔细看看。

     

    不想究其原因,只要结果。

    你吧for循环应该用线程去做。占用界面时间长的操作放到线程中。这样说明白么?

     

    这就好比你要送东西到另一个人手上,然后做饭,吃饭,结果你安排了一个人去做饭,你跑去送东西给别人,然后还要说,为什么我没有先吃好饭,然后才送到东西呢?因为你已经跑出去送东西了,没空吃饭了,另一个替你做饭的人做好饭在等你吃呢。

     

    最好的做法就是反过来。雇一个人去送东西,你自己做饭吃饭,这样东西还没送到,你就做好饭,吃好饭了。

     

    呵呵,表达能力有限,只能这样了。再不明白看看其他网友如何解释。


    2011 c# mvp China. *George读起来像不像“饺子”?我爱吃饺子,我叫George。
    • 已标记为答案 klvchen 2011年12月30日 9:18
    2011年12月30日 9:10
    版主

全部回复

  • Thread nonParameterThread = new Thread(new ThreadStart(NonParameterRun));//创建线程
    nonParameterThread.IsBackground = true;//后台线程,可以随主线程退出时退出
    nonParameterThread.Start();//开启线程①->
    this.Invalidate();//使整个窗体无效,在稍后的消息循环中,会由系统插入一个WM_PAINT并调用绘制窗体方法。
    
    //一个循环用于占用时间,同时,也让函数结束的时间延长了
    for (int z = 0; z < 312312321; z++)
    {
        int j = 2;
        int i = 1;
        int k;
        k = j / i;
    }
    //windows是一个消息驱动的操作系统
    //建议你看看c++的标准写法,main->registclass->createwindow->messageloop<--循环的处理消息-->
    //.net当然也只是对这个处理封装了,一个ui,实际状态是不停的在响应自己的消息并调用各种的消息处理函数
    //为什么你没看到?因为有很多的OnXXX的方法,例如OnPaint是在收到WM_PAINT时调用的,OnPaint中检查Paint事件
    //是否注册,如果注册过,则调用事件的响应函数。 
    //我没有扯远,下面是解答你问题的
    //接下来呢,事件响应函数执行完毕返回,OnPaint执行完毕返回,才能再次的执行消息循环,对余下的消息进行处理
    //你这里呢?你的线程通过PostMessage的方式改变界面,于是你的界面更新也就间接的排在消息队列中了,反过来,
    //既然要等待消息循环来执行,更新界面,那你的button1_click函数没执行完,button1.OnClick消息响应函数就没
    //完成,就不会处理消息,就不会更新界面。
    //所以,多线程在ui的目的就是将占用界面响应时间长的代码移到另外的线程已保证界面线程可以更快的响应消息
    //不知道我说明白没有
    



    2011 c# mvp China. *George读起来像不像“饺子”?我爱吃饺子,我叫George。
    • 已标记为答案 klvchen 2011年12月30日 9:18
    2011年12月30日 4:34
    版主
  • //多线程在ui的目的就是将占用界面响应时间长的代码移到另外的线程已保证界面线程可以更快的响应消息

    我在上面写的那个新建的那个nonParameterThread线程,就是想避开个for循环的占用时间,开个nonParameterThread线程,直接把label的内容改变,那我应该如何修改才能达到这个目的呢?
    谢谢大家~~
    
    
    2011年12月30日 7:00
  • 呼,看来我白写了。你没看懂,呵呵。最好还是仔细看看。

     

    不想究其原因,只要结果。

    你吧for循环应该用线程去做。占用界面时间长的操作放到线程中。这样说明白么?

     

    这就好比你要送东西到另一个人手上,然后做饭,吃饭,结果你安排了一个人去做饭,你跑去送东西给别人,然后还要说,为什么我没有先吃好饭,然后才送到东西呢?因为你已经跑出去送东西了,没空吃饭了,另一个替你做饭的人做好饭在等你吃呢。

     

    最好的做法就是反过来。雇一个人去送东西,你自己做饭吃饭,这样东西还没送到,你就做好饭,吃好饭了。

     

    呵呵,表达能力有限,只能这样了。再不明白看看其他网友如何解释。


    2011 c# mvp China. *George读起来像不像“饺子”?我爱吃饺子,我叫George。
    • 已标记为答案 klvchen 2011年12月30日 9:18
    2011年12月30日 9:10
    版主
  • 谢谢 George.Wuyazhe ,这样明白了,不好意思啊,我是新手,非常感谢版主的热情帮助~~~
    2011年12月30日 9:17