Android 组件间的解耦

Android模块化之组件间通信 结构描述部分 Android组件化的文章网上一搜一大推,基本上大同小异,在这里我就不再细说了。今天我主要是将我之前根据微信的架构思路的重构经验做个记录(微信Android模块化架构重构实践),这里我也主要是说组件间通信。 先讲一下我的重构目标:按照大方向的业务功能分模块,我想让我的app是由多个独立的小系统似的组成,系统间不共用业务代码完全解耦。比如我的app有主页、发现、我的三个业务模块(这... 阅读详情

EventBus、Otto, Android 自身提供的BroadcastReceiver/Intent System 和利用Handler实现的类似广播功能
用来简化应用组件间的通信。

对比主要如下:

 Otto

主要使用Bus类和两个注解@Produce, @Subscribe注解。
@Subscribe 注解告诉Bus该函数订阅了一个事件,该事件的类型为该函数的参数类型;
@Produce 注解告诉Bus该函数是一个事件产生者,产生的事件类型为该函数的返回值。

 EventBus

Event Bus 与 Otto 相比,主要有3点不同:
1.事件的订阅不是基于注解(Annotation)的,而是基于命名约定的。
在Android 4.0之前的版本中,注解解析起来比较慢,事件响应函数默认以“onEvent”开始,可以在EventBus中修改这个值,但是不推荐这么干。


2.事件响应有更多的线程选择。

Otto默认就是在Main线程中执行。

EventBus可以向不同的线程中发布事件,在ThreadMode枚举中定义了4个线程,只需要在事件响应函数名称"onEvent"后面添加对应的线程类型名称,则事件响应函数就会在对应的线程中执行。
比如事件函数"onEventAsync"就会在另外一个异步线程中执行。
四种线程类型如下:
1.PostThread: 事件响应函数和事件发布在同一个线程中执行。这个是默认值,这样可以避免线程切换而带来的消耗。
2.MainThread: 事件响应函数会在Android应用的主线程(UI线程)中执行。
3.BackgroundThread: 事件响应函数会在一个后台线程中执行。如果事件发布函数不是在主线程中,而会立即在事件发布线程中执行响应函数。但如果事件发布函数在主线程中,EventBus则会在唯一的一个后台线程中按顺序来执行所有的后台事件响应函数。
4.Async: 事件响应函数在另外一个异步线程中执行。该线程和发布线程、主线程相互独立。如果事件响应函数需要较长的时间执行,则应该使用该模式,例如网络访问等。

需要注意的是,由于系统并行的限制,应该避免在同一时间触发大量的异步线程。EventBus使用一个线程池来提高线程的效率。


3.EventBus 支持Sticky Event
有时候某个事件可能会用到多次,可以把该事件发布为Sticky Event,然后,当需要查询该信息的时候,可以通过Bus的getStickyEvent(ClassEventType)函数来查询最新发布的Event对象。
同一类型的事件只保存最新的Event对象。
注册和发布事件的函数分别为registerSticky() 和 postSticky()。

EventBus 可以解决大多数的需求,但是有没有这样一种需求??  我需要通知界面进行更新,但目前所在的界面又不需要进行更新,可不可以像这样去更新:如果当前界面需要更新,则通知当前界面进行更新,否则不更新;通知界面需要更新的,如果待更新界面不在前台,则不更新,待其被切换到前台再进行检查是否需要更新,即延迟更新。

3 利用Handler实现类似广播的功能。

相对比较灵活,不管是在UI线程或者后台线程, 都可以通过Handler发送Message 通知相应的接受者进行相应的处理,也是一个不错的选择。

不足之处:
1) 一旦有增加或者删除相应的事件,都要去修改类似消息定义配置类文件中的MSGID了。 经常改动
优点:
相对EventBus或Otto 不可以发送延迟事件, 但Handler可以post delay消息。

4 BroadcastReceiver/Intent System 

优点:

利用Android的自带的广播机制,不用像Otto, EventBus 或者Handler 专门去为了实现而写大量东西,减少了开发成本;

缺点:
1)必须register/unregister, 否则会出现内存泄漏
2)耗时操作必须与service一起使用,否则ANR.

PS:Annotation注解:

1.作用:
1)编译期间检查
Annotation具有“让编译器进行编译检查的作用”。
例如:@SuppressWarnings, @Deprecated和@Override都具有编译检查作用。

2)在反射中使用Annotation
在反射的Class,Method, Field等函数中,有许多Annotation相关的接口。这也意味着,可以在反射中解析并使用Annotation。

2. 组成部分:
每一个Annotation都与1个RetentionPolicy关联,并且与“1~n个ElementType”关联。可以通俗的理解为:
每1个Annotaion对象,都会有唯一的RetentionPolicy属性;至于ElementType属性,则有1~n个。
public enum ElementType {
    TYPE,               /* 类、接口(包括注释类型)或枚举声明  */


    FIELD,              /* 字段声明(包括枚举常量)  */


    METHOD,             /* 方法声明  */


    PARAMETER,          /* 参数声明  */


    CONSTRUCTOR,        /* 构造方法声明  */


    LOCAL_VARIABLE,     /* 局部变量声明  */


    ANNOTATION_TYPE,    /* 注释类型声明  */


    PACKAGE             /* 包声明  */
}

public enum RetentionPolicy {
    SOURCE,            /* Annotation信息仅存在于编译器处理期间,编译器处理完之后就没有该Annotation信息了  */


    CLASS,             /* 编译器将Annotation存储于类对应的.class文件中。默认行为  */


    RUNTIME            /* 编译器将Annotation存储于class文件中,并且可由JVM读入 */
}

2. Annotation 通用定义
@Documented
@Target(ElementType.Type)
@Retention(RetentionPolicy.RUNTIME)
public @interface MyAnnotation1 {

}
其中:
@interface 意味着它实现了java.lang.annotation.Annotation接口,即该注解就是一个Annotation。
定义Annotation时,@interface是必须的。 

@Documented
类和方法的Annotaion在缺省情况下是不出现在javadoc中的,如果使用@Documented修饰该Annotation,则表示它可以出现在javadoc中。
定义Annotation时,@Documented可有可无;若没有定义,则Annotation不会出现在javadoc中。

@Target(ElementType.TYPE)
ElementType是Annotation的类型属性。而@Target的作用,就是用来指定Annotation的类型属性。
定义Annotation时,@Target可有可无。若有@Target,则该Annotation只能用于它所指定的地方;若没有@Target,则该Annotation可以用于任何地方。

@Retention(RetentionPolicy.RUNTIME)
RetentionPolicy 是Annotation的策略属性,而@Retention的作用,就是指定Annotation的策略属性。
定义Annotation时,@Retention可有可无。若没有@Retention,则默认是RetentionPolicy.CLASS。
你曾遇到的某大厂奇葩问题:Android组件化开发,组件间的Activity页面跳转 1、主工程模块,主要是APP壳,里面不涉及任何逻辑代码,只有权限等配置写在app模块下的AndroidManifest.xml中。 2、常规业务模块,该层的组件就是我们真正的业务组件了。我们通常按照功能模块来划分业务组件,例如注册登录、用户个人中心、APP的首页模块等。这里的每个业务组件都是一个小的APP,只需要修改一下对应的module的build.gradle,就可以单独编译,单独打包成APK在手机上运行。 3、功能组件,一个公共模块,所有的常规业务模块都依赖他。字符串、颜色、尺寸资源等写在该模块下,该 阅读详情

相关推荐

2025.06.20【pacbio】|PB甲基化分析结果的统计与可视化介绍

本文介绍了PacBio甲基化数据的统计分析与可视化方法。主要内容包括:1) 分析甲基化位点分布、比例及染色体分布;2) 修饰基序(Motif)的统计与热图展示;3) 全基因组和局部区域测序深度可视化;4) 使用IGV查看单个reads修饰情况。文章提供了R代码示例,涵盖柱状图、分布图、热图等多种可视化形式,并建议了差异甲基化分析等进阶方法,帮助科研人员深入挖掘甲基化数据。

2066

Android组件化 -- 完全解耦实践方案

首先粘贴源码地址,欢迎frok,欢迎start 源码地址 目前,Android 组件化普遍使用于移动开发,但是组件化的初衷是为了解耦代码,并行开发效率;小型app似乎会care不到,完全解耦的组件化会在app越来越臃肿的时候带来很大的提升; ####1.组件化介绍 ok,那么我们需要知道完全解耦的组件化框架应该注意哪些点: 主app只加载业务组件,不可调用组件;组件与组件之间不存在调用关系;...

soullines的博客 5008

别再混淆了!一张图看懂SAP特殊采购类30/40/70/80的区别与选型指南

本文深度解析SAP特殊采购类30/40/70/80的核心逻辑与业务影响,通过对比框架和真实案例帮助用户掌握其适用边界。重点介绍委外加工(类型30)、工厂间转移(类型40/70)及计划与执行分离(类型80)的配置要点与常见问题,提供选型决策树和实施检查清单,助力企业优化供应链管理。

weixin_26938645的博客 453

Android 解耦(二)基于路由的解耦

在安卓开发中,随着项目的复杂度增加,模块化(或组件化)开发方式越来越受到开发者的青睐。模块化开发可以将一个大型项目拆分成多个相对独立的模块,每个模块负责一个功能或业务场景,从而提高代码的可读性、可维护性和可复用性。但是模块化开发也带来了一些挑战,其中之一就是如何实现模块间的解耦和通信。

大模型训练 479

【STM32】从零构建串口IAP框架:BootLoader与App双向跳转实战解析

本文详细解析了STM32串口IAP框架的构建,重点阐述了BootLoader与App双向跳转的实战原理与实现步骤。内容涵盖Flash分区规划、中断向量表重定向、通信协议设计及固件升级流程,并针对跳转失败、程序跑飞等常见问题提供了解决方案,帮助开发者掌握产品级远程升级的核心技术。

wind6的博客 838

CGNS快速入门到实战(二):VS配置调用CGNS静态链接库

CGNS快速入门到实战这一系列分成三篇文章展开叙述,具体有:(一)CGNS静态链接库编译;(二)VS配置调用CGNS静态链接库;(三)CGNS文件及案例展示。本篇文章重点讲述VS配置调用CGNS静态链接库。

ahang_99的博客 2618

解耦是什么意思?

通过解耦,可以减少这种依赖性,使各个组件可以独立地进行开发、测试和部署,从而更容易进行系统的维护和升级。通过定义清晰的接口和抽象层,不同的组件可以通过接口进行通信,而不需要了解彼此的具体实现细节。事件驱动的解耦方式则通过将系统的不同部分之间的通信和交互通过事件进行解耦,从而实现松耦合的系统设计。总之,解耦是一种设计原则和技术手段,旨在降低组件之间的依赖性,提高系统的灵活性和可维护性。通过解耦,不同的组件可以独立地进行开发、测试和部署,从而更好地满足系统的需求并方便后续的维护和扩展。

weixin_44943389的博客 1万+

GPS-SDR-SIM使用详解

GPS-SDR-SIM 是一款开源工具,能够生成 GPS 基带信号数据流,这些数据流可通过软件定义无线电(SDR)平台(如 ADALM-Pluto、bladeRF、HackRF、USRP 等)转换为射频(RF)信号。简单来说,它能模拟 GPS 卫星信号,帮助开发者或爱好者测试 GPS 接收设备的性能,而无需依赖真实的卫星信号。

qq_35621280的博客 1241

【Jetpack】Lifecycle 架构组件 ( 系统组件与普通组件解耦 | Lifecycle 解耦系统组件与普通组件 | 解耦服务组件与普通组件 | 监听应用程序生命周期 )

一、系统组件与普通组件解耦 二、Lifecycle 解耦 Activity 系统组件与 UI 组件 1、传统实现方式 2、LifeCycle 实现方式 三、LifecycleService 解耦 Service 与 UI 组件 1、构建脚本导入依赖 2、Android Studio 中搜索并添加依赖 3、布局文件属性排序 4、代码实现 四、ProcessLifecycleOwner 监听整个应用程序的 Activity 生命周期 1、ProcessLifecycleOwner 说明 2、代码实现

让 学习 成为一种 习惯 ( 韩曙亮 の 技术博客 ) 8410

Open3D 曲率下采样

曲率下采样是一种基于几何特征的点云处理技术,通过计算每个点的曲率来判断其所在位置的局部表面特征,从而进行选择性保留。曲率的计算通常基于点的法向量和其邻域点的分布。

纵马踏花向自由 841

ROS机器人未知环境自主探索功能包explore_lite最全源码详细解析(五)

本系列文章主要针对ROS机器人常使用的未知环境自主探索功能包explore_lite展开全源码的详细解析,并进行概括总结。 本系列文章共包含六篇文章,前五篇文章主要介绍explore_lite功能包中 explore.cpp、costmap_tools.h、frontier_search.cpp、costmap_client.cpp等源码实现文件中全部函数的详细介绍,第六篇文章进行概括总结,包含自主探索功能包explore_lite的简介,实现未知环境自主探索功能的原理及流程总结,效果演示,使用功能包exp

慕羽★的博客 1511

Android解耦(一)基于接口的module解耦

基于接口的module解耦可以通过以下几个步骤来实现: **1.**创建一个公共module(base module),并在其中定义所有需要被其他module调用或通信的接口(interface) **2.** 在各个子module中分别实现这些接口,并向公共module注册自己的实现类(implementation)。

大模型训练 535

Nuxt - 项目打包部署及上线到服务器流程(SSR 服务端渲染)

Nuxt-项目打包部署及上线到服务器流程,详细介绍Nuxt项目上线部署,服务端渲染(ssr)项目及nuxt项目部署过程,nuxt项目打包上线,Nuxt项目的部署教程,NuxtJS项目部署方案,Nuxt如何部署到线上,nuxt项目部署篇,Nuxt项目搭建到Nuxt项目部署,Nuxt项目从开始到部署,详细教程。服务器部署nuxt项目,nuxt服务端部署上线,在服务器上部署nuxt项目,NuxtJS项目——命令和部署。......

🏆 前端领域优质创作者 1万+

Android中组件间通信解耦的实现方案

在android中进行组件间拆分时,经常会遇到组件间通信的场景,一般是使用接口与实现的方式,但该方式存在一定的耦合,可能出现互相依赖的场景,为了解决该问题,就需要使用到一些组件间间解耦的方案。 方案一,使用ARouter的IProvider 1)创建一个接口类并继承自ARouter中的IProvider public interface Study extends IProvider { void open(); } 2)新建一个Study接口的实现类,并添加ARouter的注解 @Route

程序员吗? 1236

IEM模型,地表粗糙度模拟

利用微波反演土壤水分时候,利用IEM模型可以实现对随机地表的模拟

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

Android 组件化架构落地:ARouter 路由跳转与组件间通信的解耦方案

在百万级用户电商 App 中验证,组件编译速度提升 $40%$,模块间依赖减少 $90%$,核心崩溃率降至 $0.002%$ 以下。通过 ARouter 的标准化路由体系,可实现组件动态插拔,为模块热更新奠定基础。

2501_93897010的博客 385

计算机控制技术及应用

《计算机控制技术及应用》通过总结作者的科研成果和吸收国内外的先进理论、方法和技术,以计算机控制系统的网络化、开放化、智能化和集成化发展趋势为主线索,主要介绍计算机控制系统的基本概念和计算机控制系统的典型形式,计算机控制系统的数学描述与基本分析方法,以及数字PID控制器、最少拍控制系统、达林算法、状态变量设计法等设计方法及其各种改进算法。重点突出计算机控制系统输入输出通道接口的设计方法和典型控制系统的设计案例与实现方法等。

使用Event Bus模式解耦Android App组件间通信

场景描述 当一个Android应用功能越来越多的时候,保证应用的各个部分之间高效的通信将变得越来越困难。 在应用中的多个地方,控件经常需要根据某个状态来更新他们显示的内容。这种场景常见的解决方式就是定义一个接口,需要关注该事件的控件来实现这个接口。然后事件触发的地方来注册/取消注册这些对该事件感兴趣的控件。 例如,陌陌依赖手机位置信息来获取附近的用户,所以在位置更新管理器(M

hyl963254113的专栏 547

android 蓝牙通讯demo

android 下蓝牙通讯demo,实现了发现蓝牙,使能蓝牙,通过蓝牙发送消息。

Android组件间通信机解耦——Android EventBus和Otto框架

传统的事件传递方式包括:Handler、BroadCastReceiver、Interface 回调,相比之下 EventBus 的优点是代码简洁,使用简单,并将事件发布和订阅充分解耦。 EventBus 是一个 Android 事件发布/订阅框架,通过解耦发布者和订阅者简化 Android 事件传递,这里的事件可以理解为消息或者数据,本文中统一称为事件。事件传递既可用于 Android 四大组件间通讯,也可以用户异步线程和主线程间通讯等等。

凪のあすから 1894

【android】使用Event Bus模式解耦Android App组件间通信

场景描述 当一个Android应用功能越来越多的时候,保证应用的各个部分之间高效的通信将变得越来越困难。 在应用中的多个地方,控件经常需要根据某个状态来更新他们显示的内容。这种场景常见的解决方式就是定义一个接口,需要关注该事件的控件来实现这个接口。然后事件触发的地方来注册/取消注册这些对该事件感兴趣的控件。 例如,陌陌依赖手机位置信息来获取附近的用户,所以在位置更新管理器(MmL

u011494050的专栏 1117

安卓开发之EventBus使用

学完GreenDao之后再来学习下EventBus的使用,EventBus 是一个Android事件发布/订阅框架,它利用发布/订阅者者模式来对项目进行解耦,可以利用很少的代码,来实现多组件间通信/Android的组件间通信。 之前我们学习过一些传统的事件传递方式例如Handler、BroadcastReceiver等,相比之下EventBus代码简洁,使用简单,并将事件发布和订阅充分解耦。BroadcastReceiver常用于那些要与Android系统打交道的事件例如网络、电量的变化等;在Broadca

iris的博客 2172

Android组件间通信机解耦——Android EventBus和Otto框架一、前言 传统的事件传递方式包括:Handler、BroadCastReceiver、Interface 回调,相比之

一、前言 传统的事件传递方式包括:Handler、BroadCastReceiver、Interface 回调,相比之下 EventBus 的优点是代码简洁,使用简单,并将事件发布和订阅充分解耦。 EventBus 是一个 Android 事件发布/订阅框架,通过解耦发布者和订阅者简化 Android 事件传递,这里的事件可以理解为消息或者数据,本文中统一称为事件。事件传递既可

宇宙神帝 2005

使用EventBus轻松实现组件间通信

我之前写过一篇文章“Android开发之局部广播的使用”,地址:http://blog.youkuaiyun.com/jarchie520/article/details/71434833,在这篇文章里面使用的方法也能够实现今天所要讲的这个功能,组件间通信。但是那种实现方式相对来说比较麻烦,今天我们来使用一种比较流行的方式——EventBus,话说这个库现在已经更新到3.0的版本了,才想起来去说说它的用法,很...

江湖人陆仁甲 1199
上一篇: Andrioid SQLite 操作与SQLiteStatement关系
下一篇: requestFocus() 与 requestFocusFromTouch() 方法的区别
Superr爬爬虫
博客等级 码龄19年 72粉丝 93原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值