当前位置: 首页 > news >正文

Android Handler的runWithScissors方法

Handler的runWithScissors方法是隐藏API,用于执行同步任务(即让另一个线程执行一个任务,当前线程先阻塞,等待该执行完,然后当前线程再继续执行)。源码如下:

BlockingRunnable代码如下:

ok 源码就这些。 当前线程 wait(阻塞),等待handler所关联的线程执行完任务后唤醒当前线程。可以用于执行同步任务。timeOut为超时时间。

隐藏API不方便直接调用。把这段代码复制出来测试下, 测试代码如下:

package com.example.myapplication;import android.os.Handler;
import android.os.Looper;
import android.os.SystemClock;
import android.util.Log;public class Test {MyHandler handler; public void testRunWithScissors() {Thread thread1 = new Thread(){@Overridepublic void run() {Log.d("zx", "thread1 start , threadID:" + Thread.currentThread().getId());Looper.prepare();handler = new MyHandler(Looper.myLooper());Looper.loop();}};thread1.start();Thread thread2 = new Thread() {@Overridepublic void run() {Log.d("zx", "thread2 start , threadID:" + Thread.currentThread().getId());// 线程2等待线程1执行一个任务, 执行完该任务后,线程2再做其他事。boolean res = handler.runWithScissors2(new Runnable() {@Overridepublic void run() {// 线程1中会执行这个任务Log.d("zx", "current Thread, threadID:" + Thread.currentThread().getId()+ ", task start ...");for (int i = 0; i < 5; i++) {try {Thread.sleep(100);} catch (InterruptedException e) {e.printStackTrace();}Log.i("zx", "i = " + i);}Log.i("zx", "task finish");}}, 1000);Log.d("zx", "task finish, result: " + res + ", thread2 continue ...");}};try {Thread.sleep(10); // 防止线程1还没跑起来handler为空} catch (InterruptedException e) {e.printStackTrace();}thread2.start();}public static class MyHandler extends Handler {public MyHandler(Looper looper) {super(looper);}// 同步执行任务。 意思是,阻塞当前线程,等待另一个线程执行完该任务后,当前线程再继续执行. timeout为超时时间。 返回值表示任务执行是否成功public final boolean runWithScissors2(Runnable r, long timeout) { // 不能和隐藏api的方法同名,所以换了方法名。if (r == null) {throw new IllegalArgumentException("runnable must not be null");}if (timeout < 0) {throw new IllegalArgumentException("timeout must be non-negative");}if (Looper.myLooper() == getLooper()) { // 特殊情况,没有切换线程,就在当前线程执行。r.run();return true;}BlockingRunnable br = new BlockingRunnable(r);return br.postAndWait(this, timeout);}private static final class BlockingRunnable implements Runnable {private final Runnable mTask;private boolean mDone;public BlockingRunnable(Runnable task) {mTask = task;}@Overridepublic void run() {try {mTask.run();} finally {synchronized (this) {mDone = true;notifyAll();}}}public boolean postAndWait(Handler handler, long timeout) {if (!handler.post(this)) {return false;}synchronized (this) {if (timeout > 0) {final long expirationTime = SystemClock.uptimeMillis() + timeout;while (!mDone) {long delay = expirationTime - SystemClock.uptimeMillis();if (delay <= 0) {return false; // timeout 超时了}try {wait(delay);} catch (InterruptedException ex) {}}} else {while (!mDone) {try {wait();} catch (InterruptedException ex) {}}}}return true;}}}
}

然后在activity里直接测试:

打印:

ok. 结果符合预期。 

http://www.dtcms.com/a/409809.html

相关文章:

  • 180课时吃透Go语言游戏后端开发3:Go语言中其他常用的数据类型
  • 在 Android 11 上实现 WiFi 热点并发支持(同时开启 STA + AP 模式)
  • 济南高新区网站建设wordpress举报插件
  • html 占位符
  • GPT-5 Codex正式上线 Azure AI Foundry(国际版)
  • C++设计模式之结构型模式:享元模式(Flyweight)
  • STM32 智能垃圾桶项目笔记(一):超声波模块(HC-SR04)原理与驱动实现
  • 全文 -- Vortex: Extending the RISC-V ISA for GPGPU and 3D-Graphics Research
  • 设计网站推荐理由公司网站备案电话
  • 事件驱动与CDS:基于FHIR R5 Subscriptions与Bulk Data的再考察(下)
  • Tigshop开源商城系统 Java v5.2.2 / PHP v5.1.6版本正式发布(ES搜索上新)
  • 仙游县住房和城乡建设局网站1元涨1000粉丝网站
  • 【Linux】进程概念(六):进程地址空间深度解析:虚拟地址与内存管理的奥秘
  • 网站怎么做微信登录界面wordpress restful
  • Linux下写一个简陋的shell程序
  • OpenSource - 异构数据库数据与结构同步工具dbswitch
  • 首次披露潮玩成长性,量子之歌敲响新财年重估的钟声
  • jdk21 list中筛选出符合条件的list
  • Session共享问题
  • 3. Ollama 安装,流式输出,多模态,思考模型
  • Go基础:常用数学函数处理(主要是math包rand包的处理)
  • 做彩票网站被捉将受到什么惩罚北京网站建设公司制作网站
  • 沈阳小程序建设兰州seo优化
  • 低疲劳高响应!硬件软件协同:明基 RD280U 赋能创作开发,解锁新工位高效工作氛围
  • Apache Log4j2 lookup JNDI 注入漏洞(CVE-2021-44228)
  • wpf之 Popup
  • @xyflow/react:构建交互式节点流程图的完整指南
  • LinuxC++项目开发日志——基于正倒排索引的boost搜索引擎(5——通过cpp-httplib库建立网页模块)
  • 消息队列Apache Kafka教程
  • Hadess入门到实战(3) - 如何管理Npm制品