为什么主表单线程被锁定? [英] Why main form thread is locked?

查看:94
本文介绍了为什么主表单线程被锁定?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

您好,



为什么我的表单不响应以下代码的用户操作?



 使用系统; 
使用 System.Collections.Generic;
使用 System.ComponentModel;
使用 System.Data;
使用 System.Drawing;
使用 System.Text;
使用 System.Threading.Tasks;
使用 System.Windows.Forms;
使用 System.Threading;
使用 System.Net;

命名空间 SharpFive
{
public partial class Form1:Form
{
public string m_text
{
get
{
return textBox1.Text;
}
set
{
textBox1.BeginInvoke( new Action(()= > textBox1.Text = m_text + Environment.NewLine + value )) ;
}
}

私有 静态 readonly List< string> urlArray = new 列表< string>
{
http://www.google.com
http://www.bing.com
http://www.oreilly.com
http://www.simple-talk.com
http://www.microsoft.com
http://www.facebook.com
http://www.twitter.com
http://www.reddit.com
http://www.baidu.com
http://www.bbc.co.uk
};
public Form1()
{
InitializeComponent();
}

private void button1_Click( object sender,EventArgs e)
{
goingOn on = new goingOn();
foreach 字符串 domain in urlArray)
{
on.Docompute(domain);
}
}
}
class goingOn
{
private readonly Form1表单;
public goingOn(Form1表单)
{
.form =形式;
}
私有 async 任务< int> fire( string url)
{
WebClient webClient = new WebClient();
string page = await webClient.DownloadStringTaskAsync(url);
Thread.Sleep( 1000 );
return page.Length;
}
public async void Docompute( string urls)
{
int size = < span class =code-digit> 0
;
size = await fire(urls);
// form.m_text = size.ToString();
}
}
}

解决方案

这是我能看到的:你正在使用线程。睡眠。我没有v.4.5来测试它,但让我们看看:它是明确记录的,调用 async 方法不能创建一个新线程;使用它们不需要多线程: http://msdn.microsoft.com/en-us /library/vstudio/hh191443.aspx#BKMK_Threads [ ^ ]。



看起来你也没有创建任何线程。现在,让我们将这些事实与没有奇迹之类的东西的原则结合起来。你调用 Thread.Sleep 的线程是什么?这是你的UI线程。难怪它暂时没有反应迟钝。如果你经常重复它,它将永久没有反应。



你是否遵循我的逻辑?所以,看起来如果你想使用基于Sleep的模式(这本身就很好),你几乎可以使用真正的线程范例来实现它。



一般来说,我发现Microsoft声称基于异步的异步编程方法几乎在所有情况下都优于现有方法(在我上面引用的页面上)非常夸张。这在基本方面并不具有创新性,恰恰相反,当合作多线程被更广泛地使用时,它看起来像回到过去。当然,它对于模型的数量有它的价值,但它应该小心使用,护理是一些不同于线程的方式。



-SA

Hello,

Why my form does not respond on user actions with following code?

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Threading;
using System.Net;

namespace SharpFive
{    
    public partial class Form1 : Form
    {
        public string m_text
        {
            get
            {
                return textBox1.Text;
            }
            set
            {
                textBox1.BeginInvoke(new Action(() => textBox1.Text = m_text + Environment.NewLine + value));
            }
        }
        
        private static readonly List<string> urlArray = new List<string>
        {
                                                                 "http://www.google.com",
                                                                 "http://www.bing.com",
                                                                 "http://www.oreilly.com",
                                                                 "http://www.simple-talk.com",
                                                                 "http://www.microsoft.com",
                                                                 "http://www.facebook.com",
                                                                 "http://www.twitter.com",
                                                                 "http://www.reddit.com",
                                                                 "http://www.baidu.com",
                                                                 "http://www.bbc.co.uk"
        };        
        public Form1()
        {            
            InitializeComponent();           
        }       

        private void button1_Click(object sender, EventArgs e)
        {
            goingOn on = new goingOn(this);
            foreach (string domain in urlArray)
            {
                on.Docompute(domain);
            }
        }
    }
    class goingOn
    {
        private readonly Form1 form;
        public goingOn(Form1 form)
        {
            this.form = form;
        }
        private async Task<int> fire(string url)
        {
            WebClient webClient = new WebClient();
            string page = await webClient.DownloadStringTaskAsync(url);
            Thread.Sleep(1000);
            return page.Length;
        }
        public async void Docompute(string urls)
        {
            int size = 0;                      
            size = await fire(urls);            
            //form.m_text = size.ToString();
        } 
    }
}

解决方案

Here is what I can see: you are using Thread.Sleep. I don''t have v.4.5 to test it, but let''s see: it''s explicitly documented, that the invocation of async methods does not create a new thread; using them does not require multithreading: http://msdn.microsoft.com/en-us/library/vstudio/hh191443.aspx#BKMK_Threads[^].

It looks like you don''t create any threads either. Now, let''s combine these facts with the principle "there is no such thing as miracle". What is the thread where you call Thread.Sleep then? This is you UI thread. No wonder it becomes unresponsive for a while. If you repeat it on regular basis, it will be permanently unresponsive.

Did you follow my logic? So, it looks like if you want to use the pattern based on Sleep (which is itself perfectly fine), you can practically do it only using "real" threading paradigm.

Generally, I find Microsoft claim "The async-based approach to asynchronous programming is preferable to existing approaches in almost every case" (on the page I referenced above) highly exaggerated. This is not innovative in its basic aspects, just the opposite, it looks like getting back to old times when cooperative multithreading was more extensively used. It has its value, of course, for number of models, but it should be used with care, the care is some different ways than with threads.

—SA


这篇关于为什么主表单线程被锁定?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆