Android面试题库
Kotlin特性
Extensions

Kotlin 扩展函数和属性

扩展函数基础

概念和用途

  1. 定义

    • 在不修改原类的情况下为类添加新的功能
    • 可以为任何类(包括第三方库的类)添加扩展函数
    • 扩展函数在编译时被解析为静态方法
  2. 语法特点

    • 使用 fun 关键字定义
    • 接收者类型位于函数名前
    • 在函数体内可以通过 this 访问接收者对象

常见面试题

  1. 扩展函数和成员函数的区别是什么?

    答案:
    - 扩展函数在编译时被解析为静态方法,而成员函数是类的一部分
    - 扩展函数不能访问私有成员,而成员函数可以
    - 扩展函数的调用取决于变量的静态类型,而成员函数取决于实际类型
  2. 为什么需要扩展函数?

    答案:
    - 增加代码的可读性和可维护性
    - 避免创建包装类
    - 方便对现有类库进行功能扩展
    - 保持代码的整洁和模块化

扩展属性

基本概念

  1. 特点

    • 不能有初始化器
    • 必须显式提供 getter/setter
    • 不能有幕后字段(backing field)
  2. 使用场景

    • 计算属性
    • 缓存值
    • 提供便捷访问方式

实战示例

  1. 字符串扩展

    val String.lastChar: Char
        get() = this[length - 1]
     
    val String.isEmail: Boolean
        get() = matches(Regex("^[A-Za-z0-9+_.-]+@(.+)$"))
  2. 集合扩展

    val <T> List<T>.secondOrNull: T?
        get() = if (size >= 2) this[1] else null

作用域和可见性

  1. 扩展的可见性

    • 遵循普通声明的可见性规则
    • 可以在顶层声明
    • 可以在类内部声明
  2. 命名冲突解决

    • 成员函数优先于扩展函数
    • 可以使用完全限定名解决冲突

面试考点

  1. 扩展函数的调用优先级

    问:如果有同名的成员函数和扩展函数,会调用哪个?
    答:
    - 成员函数优先级高于扩展函数
    - 如果需要强制调用扩展函数,需要使用完全限定名
  2. 扩展函数的性能影响

    问:使用扩展函数会影响性能吗?
    答:
    - 扩展函数在编译时会被转换为静态方法
    - 不会产生额外的运行时开销
    - 不会创建新的类或对象

最佳实践

  1. 使用建议

    • 保持扩展函数的纯函数特性
    • 避免过度使用扩展函数
    • 合理组织扩展函数的包结构
    • 提供清晰的文档注释
  2. 常见陷阱

    • 注意空安全处理
    • 避免命名冲突
    • 注意扩展函数的可见性
    • 不要滥用扩展函数

总结

  1. 核心优势

    • 提高代码可读性
    • 增强现有类的功能
    • 保持代码整洁
    • 便于单元测试
  2. 使用场景

    • 工具类函数
    • UI组件扩展
    • 集合操作扩展
    • 字符串处理