Dart - Isolate 并发
在Dart中实现并发可以用Isolate,它是类似于线程(thread)但不共享内存的独立运行的worker,是一个独立的Dart程序执行环境。其实默认环境就是一个main isolate。
在Dart语言中,所有的Dart代码都运行在某个isolate中,代码只能使用所属isolate的类和值。不同的isolate可以通过port发送message进行交流。(首字母大写的Isolate代表Isolate对象,小写的isolate代表一个独立的Dart代码执行环境)
一个Isolate对象就是一个isolate(执行环境)的引用,通常不是当前代码所在的isolate,也就是说,当你使用Isolate对象时,你的目的应该是控制其他isolate,而不是当前的isolate。
当你要spawn(产生)一个新isolate时,如果操作成功,当前isolate会接收到一个代表新isolate的Isolate对象。
isolate在它自己的事件循环(event loop)中执行代码,每个事件都可以在该isolate的微任务队列(microtask queue)中执行更小的任务。(点击查看更多关于事件循环与微任务队列的资料)
Isolate对象允许其他isolate控制、监听它所代表的isolate的事件循环,例如当这个isolate发生未捕获错误时,可以暂停(pause)此isolate或获取(addErrorListener)错误信息。
controlPort识别并授予对isolate控制的权限,pauseCapability和terminateCapability会对某些控制操作进行权限保护。例如,暂停(pause)一个无pauseCapability的Isolate对象是不生效的。
由spawn操作创建的Isolate对象具有控制接口(control port)和控制该对象的能力(capability)。当然, 用Isolate.Isolate构造方法创建的Isolate对象可以不必带有这些能力。
Isolate对象不能用SendPort发送给另一个Isolate对象,但是控制接口(control port)和能力(capability)是可以发送的,并且可以在另一个Isolate对象中用发送来的接口与能力创建一个新的Isolate对象。
Spawn<T>方法
spawn<T>(
void entryPoint(T message),
T message, {
bool paused: false,
bool errorsAreFatal,
SendPort onExit,
SendPort onError
}
) → Future<Isolate>
创建一个与当前isolate共享代码的isolate(并不是共享内存,仅代码)。
entryPoint参数指定了调用产生的isolate时的初始函数。入口函数(entry-point function)在新isolate中以message作为唯一参数被调用。(可以想到,默认的isolate以main()函数作为入口)
这个函数必须是可以以单一参数调用的全局函数或静态方法,也就是说,它应该是接收至少一个位置参数并且最多一个必要位置参数的编译时函数常量值。只要它能用一个参数来调用,它可以接收任意数量的可选参数。它不能是函数表达式或实例方法。
初始化消息(message)通常包含一个SendPort,以便生产者与被产者互相交流。
如果paused参数赋值为true,那么这个isolate启动时就是entryPoint方法调用前的暂停状态,就像初始化时就调用了isolate.pause(isolate.pauseCapability)一样。要恢复运行,可以调用isolate.resume(isolate.pauseCapability)。
如果errorsAreFatal、 onExit 和/或 onError 参数被赋值,就相当于在isolate启动前,setErrorsFatal, addOnExitListener 和/或 addErrorListener 分别以相应参数调用。
如果忽略errorsAreFatal参数,平台会以默认行为或者继承自当前isolate的行为来处理错误。
你也可以对返回的isolate调用setErrorsFatal、addOnExitListener 和 addErrorListene等方法,但是除非isolate以pause状态启动,它在这些方法调用前可能已经执行完毕了。
示例
import 'dart:async';
import 'dart:isolate'; main() async {
var receivePort = new ReceivePort();
await Isolate.spawn(echo, receivePort.sendPort); // 'echo'发送的第一个message,是它的SendPort
var sendPort = await receivePort.first; var msg = await sendReceive(sendPort, "foo");
print('received $msg');
msg = await sendReceive(sendPort, "bar");
print('received $msg');
} /// 新isolate的入口函数
echo(SendPort sendPort) async {
// 实例化一个ReceivePort 以接收消息
var port = new ReceivePort(); // 把它的sendPort发送给宿主isolate,以便宿主可以给它发送消息
sendPort.send(port.sendPort); // 监听消息
await for (var msg in port) {
var data = msg[0];
SendPort replyTo = msg[1];
replyTo.send(data);
if (data == "bar") port.close();
}
} /// 对某个port发送消息,并接收结果
Future sendReceive(SendPort port, msg) {
ReceivePort response = new ReceivePort();
port.send([msg, response.sendPort]);
return response.first;
}
注意
目前无法在新isolate中调用平台方法(platform channel method),调用时应用会闪退且没有报错信息。
详情请看 Unable to call a platform channel method from a another isolate #13937
Flutter中文文档
Dart - Isolate 并发的更多相关文章
- Dart学习笔记
一.数据类型 1. 字符串 和 数字 互转 // String 转为 int '); assert(one == ); // String 转为 double var onePointOne = do ...
- 【dart学习】-- Dart之异步编程
一,概述 编程中的代码执行,通常分为同步与异步两种. 同步:简单说,同步就是按照代码的编写顺序,从上到下依次执行,这也是最简单的我们最常接触的一种形式.但是同步代码的缺点也显而易见,如果其中某一行或几 ...
- dart系列之:dart优秀的秘诀-隔离机制
目录 简介 dart中的隔离机制 生成一个Isolate Isolate之间的交互 一个例子 总结 简介 之前介绍了很多dart中的异步编程技巧,不知道大家有没有发现一个问题,如果是在java的异步编 ...
- Dart 2.15 现已发布
作者 / Michael Thomsen, Dart & Flutter Product Manager, Google 我们已经正式发布了 Dart SDK 的 2.15 版本,该版本新增了 ...
- isolate demo
dependencies dependencies: flutter: sdk: flutter # The following adds the Cupertino Icons font to yo ...
- Dart 基础重点截取 Dart 2 20180417
官网教程 https://www.dartlang.org/guides/language/language-tour dart是一个单线程的语言,没有多线程 Final and const If y ...
- How do you run an interactive process in Dart?
https://stackoverflow.com/questions/12682269/how-do-you-run-an-interactive-process-in-dart The test ...
- isolate sqflite demo
main.dart import 'package:flutter/material.dart'; import 'demo_isolates.dart'; import 'package:rxdar ...
- isolate 通信
main.dart import 'package:flutter/material.dart'; import 'package:flutter_isolate/flutter_isolate.da ...
随机推荐
- mac 互传文件
搭建HTTP服务,然后局域网访问就行 PHP方式: php -S 172.21.205.xxx:9999 Python python -m SimpleHTTPServer 8001 在浏览器访问:h ...
- 查询数据库中含clob,blob的表
查询含clob,blob的表select distinct ('TABLE "' || a.OWNER || '"."' || a.TABLE_NAME || '&quo ...
- 解决vue单页路由跳转后scrollTop的问题
作为vue的初级使用者,在开发过程中遇到的坑太多了.在看页面的时候发现了页面滚动的问题,当一个页面滚动了,点击页面上的路由调到下一个页面时,跳转后的页面也是滚动的,滚动条并不是在页面的顶部 在我们写路 ...
- Linux基础:用tcpdump抓包(转)
https://segmentfault.com/a/1190000012593192 https://segmentfault.com/a/1190000009691705
- awt
public class MouseTest extends Frame{ private static final long serialVersionUID = 54376853365952763 ...
- Eclipse 00: 安装教程 + 汉化 + 简单创建java项目
Java 安装教程(Eclipse) 目录: 要安装Java 要分两个步骤: 1.JDK的安装 2.Eclipse的安装 3.Eclipse汉化 4.Eclipse创建简单java项目 1和2的顺序不 ...
- CRM项目自定义的知识点
python manage.py shell #自动配置环境 a = models.CustomerInfo #实例对象可以a._meta # dir 可以查看字段方法 a._meta.app_lab ...
- Bom 字符串的问题
不含 BOM 的 UTF-8 才是标准形式",的确是这样,无BOM使用得更多些,所以个人还是推荐一般情况下用无BOM的形式吧,除非有问题的时候,再考虑换有BOM的.Windows系统保存的都 ...
- vue 之组件递归;
在开发一个 PC 端的项目时,需要开发一个树状结构,直接上效果图如下:点击 "+" 号的时候则展开下一级,点击 "-" 号的时候则收起: 之所以写这篇博客,因为 ...
- 3、jeecg 笔记之 模糊查询
1.前言 jeecg 考虑到默认模糊查询的话,会增加系统压力,导致查询慢,本来系统就挺那啥的... 2.方式一之实体赋值 实体重新赋值查询,用 * %% * 实现,我们知道 sql 中通常使用 % 去 ...