原文:WPF中的多进程(Threading)处理实例(二)

     //错误的处理
private void cmdBreakRules_Click(object sender, RoutedEventArgs e)
{
Thread thread = new Thread(UpdateTextWrong);
thread.Start();
} private void UpdateTextWrong()
{
txt.Text = "Here is some new text.";
} //正确的处理
private void cmdFollowRules_Click(object sender, RoutedEventArgs e)
{
Thread thread = new Thread(UpdateTextRight);
thread.Start();
} private void UpdateTextRight()
{
this.Dispatcher.BeginInvoke(DispatcherPriority.Normal,
(ThreadStart) delegate()
{
//txt.Text = "Here is some new text.";
UpdateText();
}
);
} private void UpdateText()
{ txt.Text = "这是更新后的文本。";
}

说明:public DispatcherOperation BeginInvoke(DispatcherPriority priority, Delegate method);其中DispatcherPriority是从-1到10 的枚举值,10优先级最高。在UpdateTextRight方法中的一下代码段

            this.Dispatcher.BeginInvoke(DispatcherPriority.Normal,
(ThreadStart)delegate()
{
//txt.Text = "Here is some new text.";
UpdateText();
}
);
可以用一下代码来替换,以增加代码的可读性
private delegate void UpdateTextDelegate();
this.Dispatcher.BeginInvoke(DispatcherPriority.Normal,new UpdateTextDelegate(UpdateText));
其实,这与上篇实例中应用的方法是相同的。

2.BackgroundWorker

2.1FindPrimesInput
FindPrimesInput

  public class FindPrimesInput
{
public int To
{ get; set; } public int From
{ get; set; } public FindPrimesInput(int from, int to)
{
To = to;
From = from;
} }
2.2 Worker
Worker

  public class Worker
{
public static int[] FindPrimes(int fromNumber, int toNumber)
{
return FindPrimes(fromNumber, toNumber, null);
} public static int[] FindPrimes(int fromNumber, int toNumber, System.ComponentModel.BackgroundWorker backgroundWorker)
{
int[] list = new int[toNumber - fromNumber]; // Create an array containing all integers between the two specified numbers.
for (int i = ; i < list.Length; i++)
{
list[i] = fromNumber;
fromNumber += ;
} //find out the module for each item in list, divided by each d, where
//d is < or == to sqrt(to)
//if the remainder is 0, the nubmer is a composite, and thus
//we mark its position with 0 in the marks array,
//otherwise the number is a prime, and thus mark it with 1 //Math.Floor 返回小于或等于指定双精度浮点数的最大整数。
int maxDiv = (int)Math.Floor(Math.Sqrt(toNumber)); int[] mark = new int[list.Length]; for (int i = ; i < list.Length; i++)
{
for (int j = ; j <= maxDiv; j++)
{ if ((list[i] != j) && (list[i] % j == ))
{
mark[i] = ;
} } int iteration = list.Length / ;
if ((i % iteration == ) && (backgroundWorker != null))
{
//BackgroundWorker.CancellationPending获取一个值,指示应用程序是否已请求取消后台操作。
if (backgroundWorker.CancellationPending)
{
// Return without doing any more work.
return null;
} //BackgroundWorker.WorkerReportsProgress 获取或设置一个值,该值指示 System.ComponentModel.BackgroundWorker 能否报告进度更新。
if (backgroundWorker.WorkerReportsProgress)
{
//float progress = ((float)(i + 1)) / list.Length * 100;
//BackgroundWorker.ReportProgress 引发 System.ComponentModel.BackgroundWorker.ProgressChanged 事件。
backgroundWorker.ReportProgress(i / iteration);
//(int)Math.Round(progress));
}
} } //create new array that contains only the primes, and return that array
int primes = ;
for (int i = ; i < mark.Length; i++)
{
if (mark[i] == )
primes += ; } int[] ret = new int[primes];
int curs = ;
for (int i = ; i < mark.Length; i++)
{
if (mark[i] == )
{
ret[curs] = list[i];
curs += ;
}
} if (backgroundWorker != null && backgroundWorker.WorkerReportsProgress)
{
backgroundWorker.ReportProgress();
} return ret; } }

2.3BackgroundWorker XAML
XAML

 <Window x:Class="Multithreading.BackgroundWorkerTest"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Multithreading" Height="323.2" Width="305.6"
xmlns:cm="clr-namespace:System.ComponentModel;assembly=System"
>
<Window.Resources>
<cm:BackgroundWorker x:Key="backgroundWorker"
WorkerReportsProgress="True" WorkerSupportsCancellation="True"
DoWork="backgroundWorker_DoWork" ProgressChanged="backgroundWorker_ProgressChanged"
RunWorkerCompleted="backgroundWorker_RunWorkerCompleted"></cm:BackgroundWorker>
</Window.Resources> <Grid Margin="5">
<Grid.RowDefinitions>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
<RowDefinition></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"></ColumnDefinition>
<ColumnDefinition></ColumnDefinition>
</Grid.ColumnDefinitions> <TextBlock Margin="5">From:</TextBlock>
<TextBox Name="txtFrom" Grid.Column="1" Margin="5">1</TextBox>
<TextBlock Grid.Row="1" Margin="5">To:</TextBlock>
<TextBox Name="txtTo" Grid.Row="1" Grid.Column="1" Margin="5">500000</TextBox> <StackPanel Orientation="Horizontal"
Grid.Row="2" Grid.Column="1">
<Button Name="cmdFind"
Margin="5" Padding="3"
Click="cmdFind_Click">Find Primes</Button>
<Button Name="cmdCancel"
Margin="5" Padding="3" IsEnabled="False"
Click="cmdCancel_Click">Cancel</Button>
</StackPanel> <TextBlock Grid.Row="3" Margin="5">Results:</TextBlock>
<ListBox Name="lstPrimes" Grid.Row="3" Grid.Column="1"
Margin="5"></ListBox> <ProgressBar Name="progressBar"
Grid.Row="4" Grid.ColumnSpan="2"
Margin="5" VerticalAlignment="Bottom" MinHeight="20"
Minimum="0" Maximum="100" Height="20"></ProgressBar>
</Grid>
</Window>

2.4 CS code
  public partial class BackgroundWorkerTest : System.Windows.Window
{
public BackgroundWorkerTest()
{
InitializeComponent();
//BackgroundWorker 在单独的线程上执行操作
//Window.FindResource(object resourceKey)搜索具有指定密钥的资源,找不到则会引发异常
backgroundWorker = ((BackgroundWorker)this.FindResource("backgroundWorker"));
} private BackgroundWorker backgroundWorker; private void cmdFind_Click(object sender, RoutedEventArgs e)
{
// Disable the button and clear previous results.
cmdFind.IsEnabled = false;
cmdCancel.IsEnabled = true;
lstPrimes.Items.Clear(); // Get the search range.
int from, to;
if (!Int32.TryParse(txtFrom.Text, out from))
{
MessageBox.Show("Invalid From value.");
return;
}
if (!Int32.TryParse(txtTo.Text, out to))
{
MessageBox.Show("Invalid To value.");
return;
} // Start the search for primes on another thread.
FindPrimesInput input = new FindPrimesInput(from, to);
backgroundWorker.RunWorkerAsync(input);
} private void backgroundWorker_DoWork(object sender, DoWorkEventArgs e)
{
// Get the input values.
FindPrimesInput input = (FindPrimesInput)e.Argument; // Start the search for primes and wait.
int[] primes = Worker.FindPrimes(input.From, input.To, backgroundWorker); //BackgroundWorker.CancellationPending 获取一个值,指示应用程序是否已请求取消后台操作。
if (backgroundWorker.CancellationPending)
{
e.Cancel = true;
return;
} // Return the result.
e.Result = primes;
} private void backgroundWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
if (e.Cancelled)
{
MessageBox.Show("Search cancelled.");
}
else if (e.Error != null)
{
// An error was thrown by the DoWork event handler.
MessageBox.Show(e.Error.Message, "An Error Occurred");
}
else
{
int[] primes = (int[])e.Result;
foreach (int prime in primes)
{
lstPrimes.Items.Add(prime);
}
}
cmdFind.IsEnabled = true;
cmdCancel.IsEnabled = false;
progressBar.Value = ;
} private void backgroundWorker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
//ProgressChangedEventArgs.ProgressPercentage 获取异步任务的进度百分比
progressBar.Value = e.ProgressPercentage;
} private void cmdCancel_Click(object sender, RoutedEventArgs e)
{
//BackgroundWorker.CancelAsync() 请求取消挂起后的操作
backgroundWorker.CancelAsync();
}
}


WPF中的多进程(Threading)处理实例(二)的更多相关文章

  1. WPF中的多进程(Threading)处理实例(一)

    原文:WPF中的多进程(Threading)处理实例(一) 说明:希望通过揣摩这些案例,能进一步了解进程的工作原理. 1.方法一描述的是在同一窗口中,在计算素数的同时而不影响Canvas的工作. 方法 ...

  2. 在WPF中自定义你的绘制(二)

    原文:在WPF中自定义你的绘制(二)   在WPF中自定义你的绘制(二)                                                                 ...

  3. WPF中的命令与命令绑定(二)

    原文:WPF中的命令与命令绑定(二) WPF中的命令与命令绑定(二)                                              周银辉在WPF中,命令(Commandi ...

  4. Python中的多进程与多线程(二)

    在上一章中,学习了Python多进程编程的一些基本方法:使用跨平台多进程模块multiprocessing提供的Process.Pool.Queue.Lock.Pipe等类,实现子进程创建.进程池(批 ...

  5. java中注解的使用与实例 (二)

    java 注解,从名字上看是注释,解释.但功能却不仅仅是注释那么简单.注解(Annotation) 为我们在代码中添加信息提供了一种形式化的方法,是我们可以在稍后 某个时刻方便地使用这些数据(通过 解 ...

  6. 二维图形的矩阵变换(二)——WPF中的矩阵变换基础

    原文:二维图形的矩阵变换(二)--WPF中的矩阵变换基础 在前文二维图形的矩阵变换(一)——基本概念中已经介绍过二维图像矩阵变换的一些基础知识,本文中主要介绍一下如何在WPF中进行矩阵变换. Matr ...

  7. 线程在WPF中的使用

    项目中可能会有这样的需求,一直获取新的某个数据信息,但仍不影响其他的操作功能,这时就用到了线程,获取新数据放到线程中操作,对其他操作不产生影响,下面就以随机获取数组中项为例解说WPF中使用线程这一实例 ...

  8. 在WPF中自定义你的绘制(一)

    原文:在WPF中自定义你的绘制(一)   在WPF中自定义你的绘制(一)                                                                 ...

  9. 在WPF中自定义控件(3) CustomControl (下)

    原文:在WPF中自定义控件(3) CustomControl (下)   在WPF中自定义控件(3) CustomControl (下)                                 ...

随机推荐

  1. NET中的System.Transactions(分布式事务)

    NET中的System.Transactions(分布式事务),当项目开发完成以后,调用的时候遇到了MSDTC的问题,在查阅了相关资料后将这个问题解决了,大致的问题主要是使用了分布式事务,而无法访问到 ...

  2. 忙里偷闲( ˇˍˇ )闲里偷学【C语言篇】——(7)结构体

    一.为什么需要结构体? 为了表示一些复杂的事物,而普通类型无法满足实际需求 二.什么叫结构体? 把一些基本类型组合在一起形成的一个新的复合数据类型叫做结构体. 三.如何定义一个结构体? 第一种方式: ...

  3. [Postgre] Insert Data into Postgre Tables

    // Insert one row INSERT INTO movies (title, release_date, count_stars, director_id) VALUES ( 'Kill ...

  4. [NPM] List available npm scripts and support tab completion

    In this lesson we will look at different ways you can list the available npm scripts. Whether we wan ...

  5. MySql批量drop table

    原文:MySql批量drop table 今天发现数据库中很多没用的表,想清理掉. 发现mysql好像不支持类似这样的写法:drop table like "%r" 在oracle ...

  6. [Angular] Difference between ViewChild and ContentChild

    *The children element which are located inside of its template of a component are called *view child ...

  7. html5--1.12表格详解

    html5--1.12表格详解 一.总结 一句话总结: 二.详解 1.表格构成三个基本要素 table:表格的范围,外框:用来定义表格,表格的其他元素包含在table标签里面: tr: 表格的行: t ...

  8. ice框架应用记录-框架说明

    ice框架是一个解决分布式问题的框架,包括应用与管理工具两部分, 应用部分主要包括: 1,注册服务,用来管理所有节点:为了可靠性,一般会开启两个注册服务,一个主注册服务一个从注册服务 2,节点,就是开 ...

  9. C++ Primer章课后编程问题

    watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvZ3V1Z2xlMjAxMA==/font/5a6L5L2T/fontsize/400/fill/I0JBQk ...

  10. Light libraries是一组通用的C基础库,目标是为减少重复造轮子而写(全部用POSIX C实现)

    Light libraries是一组通用的C基础库,目标是为减少重复造轮子而写实现了日志.原子操作.哈希字典.红黑树.动态库加载.线程.锁操作.配置文件.os适配层.事件驱动.工作队列.RPC.IPC ...