Flutter插件异步和线程

3
我有一个Flutter应用程序,使用methodchannel调用Java插件。
我试图理解线程模型和异步行为。所以流程如下:UI事件处理程序调用await methodchannel.invoke("Foo", params)。这将控制权转移给Java方法调用处理程序。在那里,我回复.success以解除在Dart中的等待。等待返回并使flutter UI事件处理程序返回。
在Java插件中,我在result.success之后继续进行更多的工作,比如说2秒。
问题是(我的问题)在这2秒内,flutter主线程/UI被阻塞了,即使flutter事件处理程序已经在2秒前返回了?为什么会这样?我可以从日志记录中看到dart和Java代码在两个单独的线程中运行。感谢您的答复。

嗯,我对你所描述的问题持怀疑态度。你所描述的是正确的,所有的Dart代码都是异步的,而且Dart和Java运行在不同的线程上,因此除非Dart正在执行一些CPU密集型的操作,否则它不应该阻塞主线程/UI。 - TruongSinh
发布你的 Java 代码:很可能你在某种程度上阻塞了 UI 主线程。 - pskink
我自己还没有使用插件,但是 await 本身并不会阻塞 UI,它只会延迟下面 await 后面的代码执行,直到返回的 Future 完成。其他异步代码仍然可以被调用(例如根据屏幕刷新速率来调用计时器、动画触发器或框架调用的其他代码)。但我不知道调用 Java 是否会阻塞 UI 线程。 - Günter Zöchbauer
3
查看这个问题 - 本地代码在本地UI线程上运行,因此您不应该阻塞它,否则会使输入和其他平台特定问题停滞。 解决方案是在单独的线程上进行额外的2秒工作。(上述问题的创建者认为您应该能够在主线程上完成工作,但似乎没有多少人同意...)关键是有一个简单的解决方法 - 后台线程。我记得之前看到过一个非常好的关于3个主要线程的图表,但现在我找不到它了。 - Richard Heap
1
谢谢大家。我对这种行为感到惊讶。但正如@RichardHeap在他的评论中提到的那样,这是按设计来的。平台插件线程与UI线程相同。所以不要阻塞它。那么,有人能解释一下这两个线程是什么吗:一个运行Flutter/Dart,另一个运行Java代码? - S. Vaghar
显示剩余3条评论
1个回答

0

Flutter默认可以处理单线程任务,但这并不意味着它会停止主线程等待Future任务。可以利用Future回调来运行并发任务,当任务完成时可以执行命令,例如使用Future.then()

如果您想深入了解,请参阅一篇关于Flutter中的Future异步任务的精心撰写的文章。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接