以下是代码: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.IO;namespace 同步调用与异步调用
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
} string SelectPath;
private void button2_Click(object sender, EventArgs e)
{
folderBrowserDialog1.ShowDialog();
SelectPath = folderBrowserDialog1.SelectedPath;
} //同步调用
private void Asynchronousjisuan(object sender, EventArgs e)
{
richTextBox1.Text += "文件夹大小为" + Asynchronouscall(SelectPath) / (1024 * 1024) + "M\n" +
Asynchronouscall(SelectPath) / 1024 + "KB\n" +
Asynchronouscall(SelectPath) + "B\n\n";
} //定义委托
private delegate long Asynchronouscalldelegate(string selectPath);
//异步调用
private void UnAsynchronousjisuan(object sender, EventArgs e)
{
Asynchronouscalldelegate d = new Asynchronouscalldelegate(Asynchronouscall);
IAsyncResult ret = d.BeginInvoke(SelectPath,null, null);
richTextBox1.Text += "正在计算当中,请稍候...\n";
long all = d.EndInvoke(ret);
richTextBox1.Text += "文件夹大小为" +all / (1024 * 1024) + "M\n" +
all / 1024 + "KB\n" +
all + "B\n\n";
} private void RemoveAll()
{
button1.Click -= Asynchronousjisuan;
button1.Click -= UnAsynchronousjisuan;
}
private void radioButton1_CheckedChanged(object sender, EventArgs e)
{
if (radioButton1.Checked == true)
{
RemoveAll();
button1.Click += Asynchronousjisuan;
}
}
private long Asynchronouscall(string selectPath)
{
DirectoryInfo ThisDir = new DirectoryInfo(selectPath);
DirectoryInfo[] ChildDirs = ThisDir.GetDirectories();
FileInfo[] files = ThisDir.GetFiles();
long totalsize = 0;
foreach (FileInfo file in files)
{
totalsize += file.Length;
}
foreach (DirectoryInfo ChildDir in ChildDirs)
{
totalsize += Asynchronouscall(ChildDir.FullName);
}
return totalsize;
} private void radioButton2_CheckedChanged(object sender, EventArgs e)
{
if (radioButton2.Checked == true)
{
RemoveAll();
button1.Click += UnAsynchronousjisuan;
}
}
}
}我不明白的是,代码是对的啊!但是在进行异步调用的时候还是要等到计算出来结果了之后才能够在richtextbox看到"正在计算当中,请稍候...\n"这句和 结果 ,不过异步调用肯定是对的,因为在进行异步计算的时候明显时间变短了。不过我就不明白了,在异步调用begin之后为何richTextBox1.Text += "正在计算当中,请稍候...\n";这句的执行效果不能够立即出现呢?我朋友用VS2010实验是对的,我是VS2008,
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.IO;namespace 同步调用与异步调用
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
} string SelectPath;
private void button2_Click(object sender, EventArgs e)
{
folderBrowserDialog1.ShowDialog();
SelectPath = folderBrowserDialog1.SelectedPath;
} //同步调用
private void Asynchronousjisuan(object sender, EventArgs e)
{
richTextBox1.Text += "文件夹大小为" + Asynchronouscall(SelectPath) / (1024 * 1024) + "M\n" +
Asynchronouscall(SelectPath) / 1024 + "KB\n" +
Asynchronouscall(SelectPath) + "B\n\n";
} //定义委托
private delegate long Asynchronouscalldelegate(string selectPath);
//异步调用
private void UnAsynchronousjisuan(object sender, EventArgs e)
{
Asynchronouscalldelegate d = new Asynchronouscalldelegate(Asynchronouscall);
IAsyncResult ret = d.BeginInvoke(SelectPath,null, null);
richTextBox1.Text += "正在计算当中,请稍候...\n";
long all = d.EndInvoke(ret);
richTextBox1.Text += "文件夹大小为" +all / (1024 * 1024) + "M\n" +
all / 1024 + "KB\n" +
all + "B\n\n";
} private void RemoveAll()
{
button1.Click -= Asynchronousjisuan;
button1.Click -= UnAsynchronousjisuan;
}
private void radioButton1_CheckedChanged(object sender, EventArgs e)
{
if (radioButton1.Checked == true)
{
RemoveAll();
button1.Click += Asynchronousjisuan;
}
}
private long Asynchronouscall(string selectPath)
{
DirectoryInfo ThisDir = new DirectoryInfo(selectPath);
DirectoryInfo[] ChildDirs = ThisDir.GetDirectories();
FileInfo[] files = ThisDir.GetFiles();
long totalsize = 0;
foreach (FileInfo file in files)
{
totalsize += file.Length;
}
foreach (DirectoryInfo ChildDir in ChildDirs)
{
totalsize += Asynchronouscall(ChildDir.FullName);
}
return totalsize;
} private void radioButton2_CheckedChanged(object sender, EventArgs e)
{
if (radioButton2.Checked == true)
{
RemoveAll();
button1.Click += UnAsynchronousjisuan;
}
}
}
}我不明白的是,代码是对的啊!但是在进行异步调用的时候还是要等到计算出来结果了之后才能够在richtextbox看到"正在计算当中,请稍候...\n"这句和 结果 ,不过异步调用肯定是对的,因为在进行异步计算的时候明显时间变短了。不过我就不明白了,在异步调用begin之后为何richTextBox1.Text += "正在计算当中,请稍候...\n";这句的执行效果不能够立即出现呢?我朋友用VS2010实验是对的,我是VS2008,
richTextBox1.Text += "正在计算当中,请稍候...\n";
后面添加这么一句就OK了
richTextBox1.Refresh();
问的东西比较多了。。=、-,不好意思,我才接触这个,忘各位大侠指教呀~
那么异步调用似乎失去了它的意义,其实不是,你在BeginInvoke后面就可以执行你想要的方法,而同时异步调用的方法也在执行,两者不冲突。调用EndInvoke就意味着你主窗口的任务完成了,只要等待异步调用返回就可以了,所以主窗口被锁住了。但无论怎样,这段过程主窗口肯定是无法动弹的,除非你不要使用异步调用,使用多线程回调就可以很好的解决主窗口被锁住的问题。你在主窗口创建一个线程,然后开始它,这时候主窗口执行少量的方法后就停下来了,但是那个新的线程还在执行,但不会锁住你的主窗口。在你的新线程里面使用this.Invoke方法让主线程操作你想要修改的窗口里面的东西,就可以在用户感觉不到的情况下修改界面上的内容了。
向上移一行
在BeginInvoke时已经锁定
不是吧,你这个还没想通?首先得确定那个BeginInvoke与EndInvoke之间的代码肯定不会给锁住,能够立刻执行的,这个只要用MessageBox.Show()测试一下就知道了,马上就弹出一个窗口的。那么问题就是richtextbox1为什么没有马上更新它的内容了,所能想到的就只有它的refresh()方法了。因为主线程在忙的时候不会刷新richtextbox1,它会得在空闲的时候才会自动刷新窗口(VS2010好像直接刷新了),但是你主线程没有空闲的时候啊,你立即执行了EndInvoke把主线程给锁住了,导致来不及刷新那个richtextbox1,那么只要在调用EndInvoke之前手工刷新一下richtextbox1就可以了。