Windows 8 Store Apps学习(43) 多线程之任务

多线程之任务: Task 基础, 多任务并行执行, 并行运算(Parallel)

介绍

重新想象 Windows 8 Store Apps 之 任务

Task - 基于线程池的任务(在 System.Threading.Tasks 命名空间下)

多 Task 的并行执行

Parallel - 并行计算(在 System.Threading.Tasks 命名空间下)

示例

1、演示 Task(基于线程池的任务)的基本应用

Thread/Tasks/TaskDemo.xaml

<Page
    x:Class="XamlDemo.Thread.Tasks.TaskDemo"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="using:XamlDemo.Thread.Tasks"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d">

    <Grid Background="Transparent">
        <StackPanel Margin="120 0 0 0">

            <TextBlock Name="lblMsg" FontSize="14.667" />

            <Button Name="btnCreateTask" Content="执行一个没有返回值的任务" Click="btnCreateTask_Click_1" Margin="0 10 0 0" />
            <Button Name="btnCancelTask" Content="取消“执行一个没有返回值的任务”" Click="btnCancelTask_Click_1" Margin="0 10 0 0" />

            <Button Name="btnCreateTaskWithReturn" Content="执行一个带返回值的任务" Click="btnCreateTaskWithReturn_Click_1" Margin="0 30 0 0" />
            <Button Name="btnCancelTaskWithReturn" Content="取消“执行一个带返回值的任务”" Click="btnCancelTaskWithReturn_Click_1" Margin="0 10 0 0" />

        </StackPanel>
    </Grid>
</Page>

Thread/Tasks/TaskDemo.xaml.cs

/*
 * Task - 基于线程池的任务(在 System.Threading.Tasks 命名空间下)
 */

using System;
using Windows.UI.Xaml;
using Windows.UI.Xaml.Controls;
using System.Threading.Tasks;
using System.Threading;
using Windows.UI.Core;

namespace XamlDemo.Thread.Tasks
{
    public sealed partial class TaskDemo : Page
    {
        /*
         * CancellationTokenSource - 用于取消 CancellationToken
         *     Token - 一个 CancellationToken 类型的对象,用于关联 Task
         *     IsCancellationRequested - 是否收到了取消操作的请求
         *     Cancel() - 发出取消操作的请求
         *
         * CancellationToken - 用于关联 Task,以便取消 Task
         *     IsCancellationRequested - 是否收到了取消操作的请求
         *     WaitHandle - 信号,可以通过 WaitHandle.WaitOne() 在当前线程等待
         *     ThrowIfCancellationRequested() - 如果收到了取消操作的请求,则抛出一个OperationCanceledException 异常
         */
        private CancellationTokenSource _cts;

        public TaskDemo()
        {
            this.InitializeComponent();
        }

        private void btnCreateTask_Click_1(object sender, RoutedEventArgs e)
        {
            _cts = new CancellationTokenSource();

            // 实例化一个 Task,可随时通过 task.Status 获取任务状态
            Task task = new Task(
                (ctx) => // 任务所调用的方法,没有返回值
                {
                    // 在当前线程上阻塞 3000 毫秒(当收到取消请求时会发出信号,停止阻塞)
                    _cts.Token.WaitHandle.WaitOne(3000);

                    // 收到取消操作的请求后抛出一个 OperationCanceledException 异常,其会导致task.IsCanceled 的值变为 true
                    // 此处的代码等同于 _cts.Token.ThrowIfCancellationRequested();
                    if (_cts.IsCancellationRequested)
                        throw new OperationCanceledException(_cts.Token);
                },
                null, // 上下文对象,task.AsyncState 可获取到此对象,上面的 ctx 也可获取到此对象
                _cts.Token // 关联的 CancellationToken 对象,用于取消操作
            );

            // 开始执行任务
            task.Start();
            // task.Wait(); 在当前线程上等待任务执行完
            lblMsg.Text = "执行了一个没有返回值的任务,3 秒后执行完毕";

            // 任务执行完毕后的处理(注:ContinueWith 方法支持任意次回调,即可以写多个task.ContinueWith() 都会被回调)
            task.ContinueWith(
                (ctx) => // 任务执行完毕后所调用的方法
                {
                    if (ctx.IsCanceled) // 任务被取消
                    {
                        var ignored = Dispatcher.RunAsync(CoreDispatcherPriority.High,
                            () =>
                            {
                                lblMsg.Text += Environment.NewLine;
                                lblMsg.Text += "取消了“执行一个没有返回值的任务”";
                            });
                    }
                    if (ctx.IsFaulted) // 任务发生了一个未处理异常
                    {
                        var ignored = Dispatcher.RunAsync(CoreDispatcherPriority.High,
                            () =>
                            {
                                lblMsg.Text += Environment.NewLine;
                                lblMsg.Text += "“执行一个没有返回值的任务”发生了一个未处理异常

";
                            });
                    }
                    if (ctx.IsCompleted) // 任务已完成(任务成功地执行完毕或被取消或发生了未处理异常都会 ctx.IsCompleted == true)
                    {
                        var ignored = Dispatcher.RunAsync(CoreDispatcherPriority.High,
                            () =>
                            {
                                lblMsg.Text += Environment.NewLine;
                                lblMsg.Text += "“执行一个没有返回值的任务”执行完成,taskId: " + ctx.Id.ToString();
                            });
                    }
                });
        }

        private void btnCancelTask_Click_1(object sender, RoutedEventArgs e)
        {
            // 发出取消操作的请求
            _cts.Cancel();
            // _cts.CancelAfter(1000); // 1000 毫秒后发出取消操作的请求
        }

        private void btnCreateTaskWithReturn_Click_1(object sender, RoutedEventArgs e)
        {
            _cts = new CancellationTokenSource();

            Func<object, string> handler = delegate(object state) // state 是传递过来的上下文对象
            {
                // 在当前线程上阻塞 3000 毫秒(当收到取消请求时会发出信号,停止阻塞)
                _cts.Token.WaitHandle.WaitOne(3000);

                // 收到取消操作的请求后抛出一个 OperationCanceledException 异常,其会导致task.IsCanceled 的值变为 true
                // 此处的代码等同于 _cts.Token.ThrowIfCancellationRequested();
                if (_cts.IsCancellationRequested)
                    throw new OperationCanceledException(_cts.Token);

                return "我是“执行一个带返回值的任务”的返回值";
            };

            // Task.Factory.StartNew() - 创建任务并马上执行,可随时通过 task.Status 获取任务状态
            // Task.Run() 同样是创建任务并马上执行
            Task<string> task = Task.Factory.StartNew<string>(
                handler, // 任务所调用的方法,带返回值
                null, // 上下文对象,task.AsyncState 可获取到此对象
                _cts.Token // 关联的 CancellationToken 对象,用于取消操作
            );
            lblMsg.Text = "执行了一个带返回值的任务,3 秒后执行完毕";

            // 任务执行完毕后的处理(注:ContinueWith 方法支持任意次回调,即可以写多个task.ContinueWith() 都会被回调)
            task.ContinueWith(
                (ctx) =>
                {
                    if (ctx.IsCanceled) // 任务被取消
                    {
                        var ignored = Dispatcher.RunAsync(CoreDispatcherPriority.High,
                            () =>
                            {
                                lblMsg.Text += Environment.NewLine;
                                lblMsg.Text += "取消了“执行一个带返回值的任务”";
                            });
                    }
                    if (ctx.IsFaulted) // 任务发生了一个未处理异常
                    {
                        var ignored = Dispatcher.RunAsync(CoreDispatcherPriority.High,
                            () =>
                            {
                                lblMsg.Text += Environment.NewLine;
                                lblMsg.Text += "“执行一个带返回值的任务”发生了一个未处理异常";
                            });
                    }
                    if (ctx.IsCompleted) // 任务已完成(任务成功地执行完毕或被取消或发生了未处理异常都会 ctx.IsCompleted == true)
                    {
                        var ignored = Dispatcher.RunAsync(CoreDispatcherPriority.High,
                            () =>
                            {
                                lblMsg.Text += Environment.NewLine;
                                lblMsg.Text += "“执行一个带返回值的任务”执行完成,taskId: " + ctx.Id.ToString();
                            });

                        // 当任务成功地执行完毕时,输出任务的返回值
                        if (!ctx.IsCanceled && !ctx.IsFaulted)
                        {
                            ignored = Dispatcher.RunAsync(CoreDispatcherPriority.High,
                            () =>
                            {
                                lblMsg.Text += Environment.NewLine;
                                // 任务的返回值
                                lblMsg.Text += ctx.Result;
                            });
                        }
                    }
                });
        }

        private void btnCancelTaskWithReturn_Click_1(object sender, RoutedEventArgs e)
        {
            // 发出取消操作的请求
            _cts.Cancel();
            // _cts.CancelAfter(1000); // 1000 毫秒后发出取消操作的请求
        }
    }
}

以上是小编为您精心准备的的内容,在的博客、问答、公众号、人物、课程等栏目也有的相关内容,欢迎继续使用右上角搜索按钮进行搜索cts
, text
, task
, 客户端取消异常
, 任务
, 一个
, 执行任务
执行完毕
,以便于您获取更多的相关知识。

时间: 2024-11-11 16:30:13

Windows 8 Store Apps学习(43) 多线程之任务的相关文章

Windows 8 Store Apps学习(48) 多线程之其他辅助类

多线程之其他辅助类: SpinWait, SpinLock, Volatile, SynchronizationContext, CoreDispatcher, ThreadLocal, ThreadStaticAttribute 介绍 重新想象 Windows 8 Store Apps 之 多线程操作的其 他辅助类 SpinWait - 自旋等待 SpinLock - 自旋锁 volatile - 必在内存 SynchronizationContext - 在指定的线程上同步数 据 CoreD

Windows 8 Store Apps学习(47) 多线程之线程同步: Semaphore等

多线程之线程同步: Semaphore, CountdownEvent, Barrier, ManualResetEvent, AutoResetEvent 介绍 重新想象 Windows 8 Store Apps 之 线程同步 Semaphore - 信号量 CountdownEvent - 通过信号数量实现线程同步 Barrier - 屏障 ManualResetEvent - 手动红绿灯 AutoResetEvent - 自动红绿灯 示例 1.演示 Semaphore 的使用 Thread

Windows 8 Store Apps学习(46) 多线程之线程同步: Lock等

多线程之线程同步: Lock, Monitor, Interlocked, Mutex, ReaderWriterLock 介绍 重新想象 Windows 8 Store Apps 之 线程同步 lock - 其实就是对 Monitor.Enter() 和 Monitor.Exit() 的一个封装 Monitor - 锁 Interlocked - 为多个线程共享的数字型变量提供原子操作 Mutex - 互斥锁,主要用于同一系统内跨进程的互斥锁 ReaderWriterLock - 读写锁 示例

Windows 8 Store Apps学习(45) 多线程之异步编程: IAsyncAction

多线程之异步编程: IAsyncAction, IAsyncOperation 重新想象 Windows 8 Store Apps (45) - 多线程之异步编程: IAsyncAction, IAsyncOperation, IAsyncActionWithProgress, IAsyncOperationWithProgress 介绍 重新想象 Windows 8 Store Apps 之 异步编程 IAsyncAction - 无返回值,无进度值 IAsyncOperation - 有返回

Windows 8 Store Apps学习(44) 多线程之异步编程

多线程之异步编程: 经典和最新的异步编程模型, IAsyncInfo 与 Task 相互转换 介绍 重新想象 Windows 8 Store Apps 之 异步编程 经典的异步编程模型(IAsyncResult) 最新的异步编程模型(async 和 await) 将 IAsyncInfo 转换成 Task 将 Task 转换成 IAsyncInfo 示例 1.使用经典的异步编程模型(IAsyncResult)实现一个支持异步操作的类 Thread/Async/ClassicAsync.cs /*

Windows 8 Store Apps学习(42) 多线程之线程池

多线程之线程池: 延迟执行, 周期执行, 在线程池中找一个线程去执行指定的方法 介绍 重新想象 Windows 8 Store Apps 之 线程池 通过 ThreadPoolTimer 实现延迟执行 通过 ThreadPoolTimer 实现周期执行 通过 ThreadPool 实现"在线程池中找一个线程去执行指定的方 法" 示例 1.通过 ThreadPoolTimer 实现延迟执行(ThreadPoolTimer 在 Windows.System.Threading 命名空间下)

Windows 8 Store Apps学习(41) 打印

介绍 重新想象 Windows 8 Store Apps 之 打印 示例 1.需要打印的文档 Print/PrintPage.xaml <Page x:Class="XamlDemo.Print.PrintPage" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xam

Windows 8 Store Apps学习(21) 动画: ThemeTransition(过渡效果)

介绍 重新想象 Windows 8 Store Apps 之 动画 ThemeTransition 的概述 EntranceThemeTransition - 页面间跳转时的过渡效果 ContentThemeTransition - 内容改变时的过渡效果 RepositionThemeTransition - 位置改变时的过渡效果 PopupThemeTransition - 弹出时的过渡效果 AddDeleteThemeTransition - 添加项或删除项时的过渡效果 ReorderThe

Windows 8 Store Apps学习(39) 契约: Share Contract

介绍 重新想象 Windows 8 Store Apps 之 契约 Share Contract - 右侧边栏称之为 Charm,其 中的"共享"称之为 Share Contract 示例 1.演示如何开发共享源 Contracts/ShareContract/ShareSource.xaml <Page x:Class="XamlDemo.Contracts.ShareContract.ShareSource" xmlns="http://sche