黑马程序员(1)---初学多线程

---------------------- ASP.Net+Android+IO开发S.Net培训、期待与您交流! ----------------------

测试准备:用vs2010创建WinForm程序

一、单线程的缺点

UI线程主要是负责跟用户交互打交道,主要监听用户操作如:拖动窗体、用户在文本框输入的值等。用户点击按钮后UI线程先响应用户点击按钮的操作调用里边的循环去了,没有线程去监听界面上的操作,就像售货员在上班时去做了别的事情用户来了没人接待一样。

二、多线程来解决问

1、前期了解知识

线程相当于一个方法,在使用多线程时首先要将方法准备好。

多线程是由主线程开启的新的线程。

多线程是由主线程开启的新的线程,它是以时间换空间,具体的执行效率要看CPU。

步骤:引入命名空间》创建线程方法--》传入要执行的方法(方法作为参数传,需要用到委托 

thread类的构造方法有两个:

 

public Thread(ParameterizedThreadStart start);

public Thread(ThreadStart start);

第一个是带参数的方法,第二个是不带参数的

2、不带参数的多线程

创建一个WinForm程序,在后台创建一个无返回值的方法

void CountTime()//创建方法
         {
            DateTime timestart = DateTime.Now;
            for (int i = 0; i < 999999999; i++)
            {
            }
            TimeSpan ts = timestart.Subtract(DateTime.Now);//从指定时间减去当前时间得到的时间差
            MessageBox.Show("ThreadOver!"+ts.TotalMilliseconds);
         }


在页面中拖一个按钮,它的点击事件如下:

private void btn_Multhread_Click(object sender, EventArgs e)

        {

            //多线程处理方法

            //线程相当于一个方法,在使用多线程时首先要将方法准备好,将循环封装成一个方法。

            Thread threadfirst = new Thread(CountTime);//方法作为参数传,需要用到委托

            //定义public delegate void ThreadStart();返回值为空,所以多线程调用的方法返回值也应该为空

            //多线程是由主线程开启的新的线程

            threadfirst.Start();

        }


3、方法重入问题

准备条件:在刚刚创建的WinForm窗体界面画出一个文本框、一个按钮,文本框的值默认为1

修改配置函数,关闭微软自带的检查:

 

 public Form1()
        {
            InitializeComponent();
            TextBox.CheckForIllegalCrossThreadCalls = false;//关闭检查
        }


义一个无返回值的函数能够实现文本框的值得增长,并且在控制台打印出来执行的哪个线程、结果是什么、执行了多少次:

void changeText()
        {
            for (int i = 0; i < 1000; i++)
            {
                int a = int.Parse(txt_num.Text);
                Console.WriteLine(Thread.CurrentThread+"a="+a);
                a++;
                txt_num.Text = a.ToString();
            }
        }


按钮点击事件:

 

 private void btn_reset_Click(object sender, EventArgs e)
        {
        Thread thread = new Thread(changeText);
            thread.Name = "t1";
            thread.IsBackground = true;
            thread.Start();

            Thread thread2 = new Thread(changeText);
            thread2.Name = "t2";
            thread2.IsBackground = true;
            thread2.Start();
        }


理论上应出现的结果是2000,实际执行结果:1004。

原因:在线程t1还没执行完毕时,cpu开始执行t2,t2的值还是原来的的文本框的值,待t2还没执行完毕,cpu又开始执行t1…….  

 

实际上是t1走了1000次,t2也执行了1000

看控制台输出:(t1,t2是线程,a是执行时的值,i是执行次数)

t1,a=994,i=998

t2,a=995,i=993

t1,a=995,i=999

t2,a=996,i=994

t2,a=997,i=995

t2,a=998,i=996

t2线程 't2' (0x22b0) 已退出,返回值为 0 (0x0)。

,a=999,i=997

t2,a=1000,i=998

t2,a=1001,i=999

4、带参数的多线程

 

thread类的另外一个带参数的构造方法:

 

-------------------------执行带一参数的方法------------------------------

public Thread(ParameterizedThreadStart start);它的定义如下
public delegate void ParameterizedThreadStart(object obj);参数类型是object类型
void GetName(object name)
        {
            if (name != null)
                MessageBox.Show("name=" + name.ToString());
            else
                MessageBox.Show("null");
        }
        private void btn_threadWithParm_Click(object sender, EventArgs e)
        {
            //ParameterizedThreadStart pts = new ParameterizedThreadStart(GetName);//声明带参数的委托
            //Thread thread = new Thread(pts);
            //执行带参数的方法
            Thread thread = new Thread(GetName);//直接把方法写进去
            thread.IsBackground = true;
            thread.Start(txt_name.Text);//start也有两种类型,其一是带参数的
        }


 

//-------------------------执行带多个参数的方法-------------------------
        void GetName2(object li)
        {
            List<string> list = li as List<string>;//泛型方法
            if (list != null)
            {
                foreach (var s in list)
                {
                    MessageBox.Show(s);
                }
            }
        }
        private void btn_WithManyParam_Click(object sender, EventArgs e)
        {
            Thread thread = new Thread(GetName2);
            thread.IsBackground = true;
            thread.Start(new List<string> {"张三","李四","王五"});
        }



---------------------- ASP.Net+Android+IO开发S.Net培训、期待与您交流! ----------------------

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值