设计模式 -> 策略模式(Strategy Pattern)

前言

Android开发中,策略模式是一种常用的设计模式,它能够让我们在运行时动态选择算法或行为。本文将重点介绍如何在Android中安全地实现策略模式,避免内存泄漏问题。

传统策略模式的问题

kotlin 复制代码
// ❌ 存在内存泄漏风险的实现
object LazyStart : StartStrategy {
    override operator fun invoke(block: suspend () -> Unit) {
        GlobalScope.launch {
            delay(1000)  
            // 延迟执行可能导致内存泄漏,block表达式持有的Activity/Fragment可能销毁后再执行,导致Activity/Fragment无法被GC
            block()
        }
    }
}

// 危险使用场景
class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        
        LazyStart {
            updateUI()  // Activity可能已销毁,但lambda仍被执行
        }
    }
}

✅ 内存安全的解决方案

方案1:Class实现 + 作用域绑定

kotlin 复制代码
class SafeImmediateStart(private val scope: CoroutineScope) : StartStrategy {
    override operator fun invoke(block: suspend () -> Unit) {
        scope.launch {
            block()
        }
    }
}

class SafeLazyStart(private val scope: CoroutineScope) : StartStrategy {
    override operator fun invoke(block: suspend () -> Unit) {
        scope.launch {
            delay(1000)
            block()
        }
    }
}

// 安全使用
class MainActivity : AppCompatActivity() {
    private val immediateStrategy = SafeImmediateStart(lifecycleScope)
    private val lazyStrategy = SafeLazyStart(lifecycleScope)
    
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        
        immediateStrategy {
            updateUI()  // 安全:Activity销毁时协程自动取消
        }
    }
}

方案2:枚举实现 + 作用域绑定

kotlin 复制代码
enum class SafeStartStrategy {
    IMMEDIATE {
        override fun execute(scope: CoroutineScope, block: suspend () -> Unit) {
            scope.launch { block() }
        }
    },
    
    LAZY {
        override fun execute(scope: CoroutineScope, block: suspend () -> Unit) {
            scope.launch {
                delay(1000)
                block()
            }
        }
    };
    
    abstract fun execute(scope: CoroutineScope, block: suspend () -> Unit)
    
    operator fun invoke(scope: CoroutineScope, block: suspend () -> Unit) {
        execute(scope, block)
    }
}

// 使用方式
class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        
        SafeStartStrategy.LAZY(lifecycleScope) {
            updateUI()
        }
    }
}

实际应用场景

kotlin 复制代码
// 内存安全检查清单
class MemorySafeStrategy(
    private val scope: CoroutineScope  // ✅ 1. 绑定正确作用域
) : StartStrategy {
    override operator fun invoke(block: suspend () -> Unit) {
        scope.launch {  // ✅ 2. 使用传入的scope
            try {
                block()
            } catch (e: CancellationException) {
                // ✅ 3. 处理取消异常
                Log.d("Strategy", "Execution cancelled")
            }
        }
    }
}

核心总结

场景 推荐方案 原因
UI操作 Class + lifecycleScope 绑定Activity生命周期
数据处理 Class + viewModelScope 绑定ViewModel生命周期
简单工具 改进枚举 + scope参数 简洁且安全
相关推荐
咖啡八杯6 小时前
GoF设计模式——中介者模式
java·后端·spring·设计模式
杉氧12 小时前
深入理解 Compose 重组机制:快照系统如何驱动 UI 精准刷新?
android·架构·android jetpack
召钱熏12 小时前
状态枚举正确≠渲染正确:一个语音按钮的状态机边界修复实录
android·前端
杉氧13 小时前
深度解析:Jetpack Compose 核心架构与底层原理 —— 十年安卓老兵的“破茧重生”
android·架构·android jetpack
通玄13 小时前
Jetpack Compose 入门系列(七):ViewModel 与界面状态管理
android
落魄Android在线炒饭13 小时前
Android Framework 开发技巧:android.jar 生成与系统快速编译验证
android
如此风景14 小时前
Kotlin Flow操作符学习
android·kotlin
plainGeekDev15 小时前
GreenDAO → Room
android·java·kotlin
weiggle15 小时前
第八篇:ViewModel + Compose——生产级状态管理实践
android
胡萝卜术19 小时前
从“分数打架”到“排名投票”:为什么你的ChatBI必须用RRF?
算法·设计模式·面试