Android 常用设计模式速查
2026/9/8 17:38:15 网站建设 项目流程

本文整理 Android 开发中常见技术点对应的设计模式,并给出简化伪代码、典型源码/原理使用位置。伪代码用于理解模式结构,不等同于源码实现。

总览

设计模式Android 常见技术点典型使用位置
单例模式全局管理器、系统服务、数据库实例WorkManager.getInstance()Room.databaseBuilder()后的数据库单例、SystemServiceRegistry
Builder 模式复杂对象构建AlertDialog.BuilderNotificationCompat.BuilderRoom.databaseBuilder()
工厂模式对象创建解耦LayoutInflater.Factory2FragmentFactoryViewModelProvider.Factory
观察者模式数据变化通知、生命周期感知LiveData.observe()LifecycleObserverFlow.collect
适配器模式数据和 UI 解耦RecyclerView.AdapterListAdapterCursorAdapter
代理模式IPC、远程服务、本地接口代理Binder 的Stub/Proxy、AIDL
装饰器模式包装并增强能力ContextWrapperContextThemeWrapperInputStream包装链
外观模式简化复杂子系统访问ContextCameraXGlide.with()
模板方法模式固定流程中暴露可重写步骤Activity生命周期、View.draw()ViewGroup.dispatchDraw()
策略模式可替换算法或行为RecyclerView.LayoutManagerItemAnimatorDiffUtil.ItemCallback
责任链模式事件分发、拦截链触摸事件分发、OkHttp Interceptor
状态模式对象行为随状态变化Lifecycle.State、播放器状态、登录状态
命令模式把操作封装为对象Runnable+HandlerPendingIntent、点击事件回调
MVC / MVP / MVVM应用架构分层Activity/FragmentViewModelLiveData/StateFlow、Repository

1. 单例模式 Singleton

使用场景

  • 应用内只有一个实例:数据库、配置中心、线程池、日志工具。
  • Android 系统服务通过统一入口获取共享服务。
  • 避免重复创建重资源对象。

Android 中的例子

  • WorkManager.getInstance(context)
  • RoomDatabase通常在应用层做单例封装
  • SystemServiceRegistry管理系统服务实例
  • Application全局生命周期入口

伪代码

classAppDatabaseprivateconstructor(){companionobject{@Volatileprivatevarinstance:AppDatabase?=nullfungetInstance():AppDatabase{returninstance?:synchronized(this){instance?:AppDatabase().also{instance=it}}}}}

源码 / 原理标注

  • Context.getSystemService()背后会从系统服务注册表中按名称获取服务。
  • WorkManager通过getInstance()对外提供统一入口,内部保证调度组件可被全局访问。
  • Room 数据库实例创建成本较高,官方实践通常建议在应用进程内复用单例。

2. Builder 模式

使用场景

  • 对象参数很多,构造函数会变得臃肿。
  • 创建过程需要链式配置。
  • 最终通过build()create()生成目标对象。

Android 中的例子

  • AlertDialog.Builder
  • NotificationCompat.Builder
  • Room.databaseBuilder(context, AppDatabase::class.java, "db").build()
  • WorkRequest.Builder

伪代码

classDialogprivateconstructor(valtitle:String?,valmessage:String?,valcancelable:Boolean){classBuilder{privatevartitle:String?=nullprivatevarmessage:String?=nullprivatevarcancelable:Boolean=truefunsetTitle(value:String)=apply{title=value}funsetMessage(value:String)=apply{message=value}funsetCancelable(value:Boolean)=apply{cancelable=value}funbuild():Dialog{returnDialog(title,message,cancelable)}}}

源码 / 原理标注

  • AlertDialog.Builder先收集标题、按钮、布局等配置,最后调用create()构建AlertDialog
  • NotificationCompat.Builder把通知图标、标题、内容、渠道等复杂参数集中封装,降低构造复杂度。
  • Room 的 builder 会配置数据库名、迁移策略、线程策略,最后创建数据库实例。

3. 工厂模式 Factory

使用场景

  • 调用方不直接依赖具体类构造函数。
  • 根据条件创建不同对象。
  • 框架希望把对象创建权开放给开发者定制。

Android 中的例子

  • LayoutInflater.Factory2创建 View
  • FragmentFactory创建 Fragment
  • ViewModelProvider.Factory创建 ViewModel
  • ServiceLoader或依赖注入框架中的对象创建

伪代码

interfaceViewModelFactory{fun<T:ViewModel>create(modelClass:Class<T>):T}classUserViewModelFactory(privatevalrepository:UserRepository):ViewModelFactory{overridefun<T:ViewModel>create(modelClass:Class<T>):T{if(modelClass==UserViewModel::class.java){returnUserViewModel(repository)asT}error("Unknown ViewModel")}}

源码 / 原理标注

  • ViewModelProvider不知道业务ViewModel如何构造,于是通过Factory把创建过程交给调用方。
  • LayoutInflater解析 XML 时,需要把标签名转换成具体View对象,这就是典型的创建型模式场景。
  • FragmentFactory允许 Fragment 使用带参数构造或依赖注入方式创建,避免框架只能调用空构造。

4. 观察者模式 Observer

使用场景

  • 一个对象状态变化,需要通知多个观察者。
  • UI 自动响应数据变化。
  • 生命周期变化需要通知监听者。

Android 中的例子

  • LiveData.observe(owner, observer)
  • Lifecycle.addObserver(observer)
  • StateFlow/SharedFlow
  • TextWatcherBroadcastReceiver

伪代码

classObservableData<T>{privatevalobservers=mutableListOf<(T)->Unit>()privatevarvalue:T?=nullfunobserve(observer:(T)->Unit){observers+=observer value?.let(observer)}funsetValue(newValue:T){value=newValue observers.forEach{it(newValue)}}}

源码 / 原理标注

  • LiveData保存观察者列表,数据变化后分发给活跃生命周期状态下的观察者。
  • LifecycleRegistry内部维护观察者,并在Activity/Fragment生命周期变化时派发生命周期事件。
  • BroadcastReceiver可以理解为系统级发布订阅机制,发送广播后匹配的接收者会收到通知。

5. 适配器模式 Adapter

使用场景

  • 将一种接口转换成另一种接口。
  • 数据结构和 UI 展示组件不直接耦合。
  • 让已有数据适配目标控件协议。

Android 中的例子

  • RecyclerView.Adapter
  • ListAdapter
  • CursorAdapter
  • PagerAdapter

伪代码

classUserAdapter(privatevalusers:List<User>):RecyclerView.Adapter<UserViewHolder>(){overridefungetItemCount():Int{returnusers.size}overridefunonCreateViewHolder(parent:ViewGroup,viewType:Int):UserViewHolder{returnUserViewHolder(parent.inflate("item_user"))}overridefunonBindViewHolder(holder:UserViewHolder,position:Int){holder.bind(users[position])}}

源码 / 原理标注

  • RecyclerView不关心数据来源,只依赖Adapter提供数量、创建 ViewHolder、绑定数据。
  • CursorAdapter把数据库查询结果Cursor适配成列表项视图。
  • ListAdapter在适配器基础上加入DiffUtil,让列表更新更高效。

6. 代理模式 Proxy

使用场景

  • 调用方访问的是代理对象,代理对象再转发给真实对象。
  • 可以隐藏跨进程、远程、权限校验、缓存等复杂细节。
  • Android IPC 是代理模式的经典场景。

Android 中的例子

  • Binder IPC 中的StubProxy
  • AIDL 自动生成代码
  • 系统服务接口,例如ActivityManagerPackageManager

伪代码

interfaceIUserService{fungetUserName(id:Long):String}classUserServiceProxy(privatevalremoteBinder:Binder):IUserService{overridefungetUserName(id:Long):String{valdata=Parcel.obtain()valreply=Parcel.obtain()data.writeLong(id)remoteBinder.transact(CODE_GET_USER,data,reply,0)returnreply.readString()}}

源码 / 原理标注

  • AIDL 会生成StubProxy:本地进程调用接口方法,实际由Proxy封装参数并通过 Binder 发送到远端。
  • 客户端拿到的很多系统服务接口并不是真实服务对象,而是 Binder 代理。
  • Proxy屏蔽了进程边界,让跨进程调用看起来像普通方法调用。

7. 装饰器模式 Decorator

使用场景

  • 不修改原类的情况下增强对象能力。
  • 多层包装,逐步叠加功能。
  • 保持原始接口一致。

Android 中的例子

  • ContextWrapper
  • ContextThemeWrapper
  • Java IO 中的BufferedInputStream(InputStream)
  • AppCompat 中对ContextView的包装增强

伪代码

openclassBaseContext{openfungetThemeName():String="Default"}openclassContextWrapper(privatevalbase:BaseContext):BaseContext(){overridefungetThemeName():String{returnbase.getThemeName()}}classThemeContextWrapper(base:BaseContext,privatevaltheme:String):ContextWrapper(base){overridefungetThemeName():String{returntheme}}

源码 / 原理标注

  • ContextWrapper内部持有一个base Context,默认把大部分调用委托给它。
  • ContextThemeWrapper在原有Context基础上叠加主题能力。
  • Activity本身也继承自ContextThemeWrapper,因此具备上下文和主题相关能力。

8. 外观模式 Facade

使用场景

  • 对外暴露简单接口,内部封装复杂子系统。
  • 降低调用方理解成本。
  • 常用于 SDK、框架入口、工具库入口。

Android 中的例子

  • Context封装资源、文件、服务、启动组件等能力
  • Glide.with(context).load(url).into(imageView)
  • CameraX相比 Camera2 提供更简单的相机 API
  • NavController封装 Fragment 事务和回退栈

伪代码

classImageLoaderFacade(privatevalcache:ImageCache,privatevalnetwork:ImageNetwork,privatevaldecoder:ImageDecoder){funload(url:String,imageView:ImageView){valbytes=cache.get(url)?:network.download(url)valbitmap=decoder.decode(bytes)imageView.setImageBitmap(bitmap)}}

源码 / 原理标注

  • Context是 Android 应用访问系统能力的重要外观,调用方无需知道资源管理器、包管理器、服务管理器的内部细节。
  • CameraX把 Camera2 中复杂的设备枚举、Session、CaptureRequest 封装成更容易使用的用例 API。
  • NavController把导航图、参数、Fragment 切换、返回栈管理封装成统一入口。

9. 模板方法模式 Template Method

使用场景

  • 父类定义算法骨架。
  • 子类只重写流程中的部分步骤。
  • 框架控制整体流程,业务代码填充细节。

Android 中的例子

  • Activity.onCreate()onStart()onResume()
  • Fragment生命周期
  • View.draw()中的测量、绘制、子 View 绘制流程
  • BaseAdapter.getView()

伪代码

abstractclassBaseActivity{funperformCreate(){attachBaseContext()onCreate()restoreState()}protectedopenfunattachBaseContext(){}protectedabstractfunonCreate()protectedopenfunrestoreState(){}}classMainActivity:BaseActivity(){overridefunonCreate(){setContentView("activity_main")}}

源码 / 原理标注

  • Android Framework 决定生命周期调用顺序,开发者只重写指定回调。
  • View.draw()内部大致按背景、内容、子 View、前景等步骤绘制,子类可重写onDraw()填充自定义绘制。
  • 模板方法体现了“框架调用业务代码”的控制反转思想。

10. 策略模式 Strategy

使用场景

  • 同一个上下文中切换不同算法或行为。
  • 行为对象可以独立替换。
  • 减少大量if else

Android 中的例子

  • RecyclerView.LayoutManager
  • RecyclerView.ItemAnimator
  • DiffUtil.ItemCallback
  • 动画插值器Interpolator

伪代码

interfaceSortStrategy{funsort(items:List<Item>):List<Item>}classTimeSortStrategy:SortStrategy{overridefunsort(items:List<Item>)=items.sortedBy{it.time}}classNameSortStrategy:SortStrategy{overridefunsort(items:List<Item>)=items.sortedBy{it.name}}classItemController(privatevarstrategy:SortStrategy){funrender(items:List<Item>){show(strategy.sort(items))}}

源码 / 原理标注

  • RecyclerView通过替换LinearLayoutManagerGridLayoutManagerStaggeredGridLayoutManager改变布局策略。
  • Interpolator决定动画数值随时间变化的策略,例如线性、加速、减速。
  • DiffUtil.ItemCallback把“如何判断两个 item 是否相同”的策略交给业务层。

11. 责任链模式 Chain of Responsibility

使用场景

  • 请求沿着一条链传递。
  • 链上每个节点都有机会处理或继续传递。
  • 常用于事件分发、请求拦截、日志处理。

Android 中的例子

  • 触摸事件分发:Activity->Window->DecorView->ViewGroup->View
  • ViewGroup.dispatchTouchEvent()onInterceptTouchEvent()onTouchEvent()
  • OkHttp Interceptor拦截器链

伪代码

abstractclassEventNode{varnext:EventNode?=nullfundispatch(event:MotionEvent):Boolean{if(handle(event)){returntrue}returnnext?.dispatch(event)?:false}protectedabstractfunhandle(event:MotionEvent):Boolean}

源码 / 原理标注

  • 触摸事件先到Activity.dispatchTouchEvent(),再进入Window和根 View。
  • ViewGroup可以通过onInterceptTouchEvent()决定是否拦截事件。
  • 如果子 View 不消费事件,事件可能回到父容器或自身的onTouchEvent()继续处理。
  • OkHttp 的应用拦截器、重试拦截器、缓存拦截器、网络拦截器按链式顺序处理请求。

12. 状态模式 State

使用场景

  • 对象在不同状态下行为不同。
  • 状态转换规则比较清晰。
  • 避免状态相关逻辑散落在多个条件分支中。

Android 中的例子

  • Lifecycle.State
  • 播放器状态:Idle、Preparing、Playing、Paused、Completed
  • 登录状态:Guest、LoggedIn、Expired
  • 下载任务状态:Pending、Running、Success、Failed

伪代码

interfacePlayerState{funplay(player:Player)funpause(player:Player)}classIdleState:PlayerState{overridefunplay(player:Player){player.prepare()player.state=PlayingState()}overridefunpause(player:Player){// Idle 状态下无需处理}}classPlayingState:PlayerState{overridefunplay(player:Player){}overridefunpause(player:Player){player.pauseInternal()player.state=PausedState()}}

源码 / 原理标注

  • LifecycleRegistry会在生命周期事件发生时推进内部状态,例如INITIALIZEDCREATEDSTARTEDRESUMED
  • UI 层常用状态驱动渲染,例如 Loading、Content、Empty、Error。
  • 播放器、下载器、上传器这类组件很适合用状态模式管理行为。

13. 命令模式 Command

使用场景

  • 把一个操作封装成对象。
  • 操作可以延迟执行、排队执行、撤销或重试。
  • 调用者和执行者解耦。

Android 中的例子

  • Runnable投递到Handler
  • PendingIntent
  • View.OnClickListener
  • WorkRequest

伪代码

interfaceCommand{funexecute()}classSaveUserCommand(privatevalrepository:UserRepository,privatevaluser:User):Command{overridefunexecute(){repository.save(user)}}classCommandQueue{privatevalcommands=ArrayDeque<Command>()funenqueue(command:Command){commands.addLast(command)}funrunNext(){commands.removeFirstOrNull()?.execute()}}

源码 / 原理标注

  • Handler.post(Runnable)把一段逻辑封装为Runnable,放入消息队列等待主线程或工作线程执行。
  • PendingIntent把未来要执行的启动 Activity、Service、Broadcast 操作交给系统保存并触发。
  • WorkRequest把后台任务的执行条件、输入数据、调度要求封装起来,由 WorkManager 统一执行。

14. MVC / MVP / MVVM 架构模式

使用场景

  • 组织应用层代码职责。
  • 降低 UI、业务逻辑、数据源之间的耦合。
  • 提高可测试性和可维护性。

Android 中的例子

  • MVC:早期Activity同时承担 Controller 和部分 View 职责。
  • MVP:Activity/Fragment作为 View,Presenter 处理业务逻辑。
  • MVVM:ViewModel暴露状态,Activity/Fragment/Compose负责渲染。
  • Repository:隔离网络、数据库、缓存等数据来源。

伪代码

classUserViewModel(privatevalrepository:UserRepository):ViewModel(){privateval_uiState=MutableStateFlow<UserUiState>(UserUiState.Loading)valuiState:StateFlow<UserUiState>=_uiStatefunloadUser(id:Long){viewModelScope.launch{_uiState.value=UserUiState.Loading _uiState.value=runCatching{repository.getUser(id)}.fold(onSuccess={UserUiState.Content(it)},onFailure={UserUiState.Error(it.message.orEmpty())})}}}classUserFragment:Fragment(){privatevalviewModel:UserViewModelbyviewModels()funrender(){collect(viewModel.uiState){state->when(state){isUserUiState.Loading->showLoading()isUserUiState.Content->showUser(state.user)isUserUiState.Error->showError(state.message)}}}}

源码 / 原理标注

  • ViewModel生命周期长于配置变化后的Activity/Fragment重建,适合保存 UI 状态。
  • LiveData/StateFlow让 View 观察状态变化,体现观察者模式。
  • Repository 隔离数据来源,让 UI 层不直接依赖 Retrofit、Room、DataStore 等具体实现。
  • Jetpack Compose 中常见的State -> UI思路也是 MVVM / 单向数据流思想的延伸。

15. 组合模式 Composite

使用场景

  • 树形结构中,单个对象和组合对象使用统一接口。
  • 调用方可以一致地处理叶子节点和容器节点。

Android 中的例子

  • ViewViewGroup
  • 菜单结构Menu/MenuItem
  • Compose UI 树

伪代码

abstractclassUiNode{abstractfundraw()}classTextNode:UiNode(){overridefundraw(){drawText()}}classContainerNode:UiNode(){privatevalchildren=mutableListOf<UiNode>()funadd(child:UiNode){children+=child}overridefundraw(){children.forEach{it.draw()}}}

源码 / 原理标注

  • ViewGroup继承自View,因此容器本身也是一个 View。
  • ViewGroup内部持有子 View 列表,测量、布局、绘制时会递归处理子节点。
  • Compose 运行时维护 UI 组合树,状态变化后按树结构进行重组和更新。

16. 享元模式 Flyweight

使用场景

  • 大量相似对象共享内部状态,减少内存开销。
  • 缓存可复用对象。
  • 图片、字符串、资源对象等都可能用到共享思想。

Android 中的例子

  • Bitmap缓存
  • RecyclerView复用ViewHolder
  • 资源系统复用DrawableColorStateList等资源数据
  • 字符串常量池

伪代码

classBitmapPool{privatevalcache=mutableMapOf<String,Bitmap>()funget(key:String,loader:()->Bitmap):Bitmap{returncache[key]?:loader().also{bitmap->cache[key]=bitmap}}}

源码 / 原理标注

  • RecyclerView通过回收池复用 ViewHolder,避免列表滑动时频繁创建 View。
  • 图片加载库通常使用内存缓存、磁盘缓存、Bitmap 池降低内存抖动。
  • Android 资源加载系统会缓存部分资源,避免重复解析和创建。

记忆方式

你在做什么常见模式
创建复杂对象Builder
控制对象唯一Singleton
把创建权交出去Factory
数据变了通知 UIObserver
数据接到列表控件Adapter
跨进程像本地调用Proxy
包一层增强功能Decorator
给复杂系统一个简单入口Facade
框架定流程,业务填步骤Template Method
替换算法或行为Strategy
请求一路传递Chain of Responsibility
不同状态不同行为State
操作排队或延迟执行Command
树形 UI 统一处理Composite
大量对象共享复用Flyweight

学习建议

  • 看源码时先问:这个类是在创建对象、转发调用、分发事件、保存状态,还是适配数据?
  • Android Framework 很多模式不是“标准教科书写法”,而是为了生命周期、IPC、UI 树、线程模型做了工程化变体。
  • 面试回答时建议按“三段式”:先说模式定义,再说 Android 例子,最后说源码或原理中的关键调用链。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询