2-2-8 快速掌握Kotlin-vararg关键字与get函数

🌟 Kotlin的vararg关键字与get函数:完美组合!

嘿!看到你对Kotlin的vararg关键字和get函数感兴趣,太棒了!这两个特性组合起来能让你的代码既灵活又优雅,就像给你的代码装上了"万能插头"一样!😄

🧩 vararg关键字:让参数数量"自由"起来

vararg (variable number of arguments)是Kotlin中用于定义可变数量参数的关键字,它允许函数接收任意数量的同类型参数。

基本用法

kotlin 复制代码
fun sum(vararg numbers: Int): Int {
    var total = 0
    for (num in numbers) {
        total += num
    }
    return total
}

// 调用示例
println(sum(1, 2, 3))       // 6
println(sum(1, 2, 3, 4, 5)) // 15
println(sum())              // 0(0个参数)

重要提示

  • vararg参数必须是最后一个参数
  • 不能将数组直接传递给vararg参数(会报类型不匹配错误)
  • 如果需要传递数组,可以使用*操作符

🧩 get函数:属性访问与数组索引

get函数在Kotlin中通常用于:

  1. 属性的getter(访问属性值)
  2. 重载[]运算符,实现类似数组的索引访问

基本用法

kotlin 复制代码
// 属性的getter
class Person {
    var name: String = "John"
        get() {
            println("Getting name: $field")
            return field
        }
}

// 重载[]运算符
class MyList<T>(vararg items: T) {
    private val list = items.toList()
    
    operator fun get(index: Int): T {
        return list[index]
    }
}

fun main() {
    val list = MyList(1, 2, 3, 4)
    println(list[2]) // 3
}

🔥 vararg与get函数的完美结合

现在,让我们看看它们如何组合使用,打造一个"万能士兵"类:

实战示例

kotlin 复制代码
class Soldier<T : Weapon>(vararg _items: T) {
    var items: Array<out T> = _items
    
    // 重载[]运算符,实现通过索引获取武器
    operator fun get(index: Int): T? {
        return items[index]
    }
    
    fun fight() {
        for (item in items) {
            item.fire()
        }
    }
}

open class Weapon(var name: String) {
    open fun fire() {
        println("Weapon fire!")
    }
}

class AK47 : Weapon("AK47") {
    override fun fire() {
        super.fire()
        println("AK47 fire fire!")
    }
}

class T72 : Weapon("T72") {
    override fun fire() {
        super.fire()
        println("T72 fire fire!")
    }
}

fun main() {
    val soldier = Soldier(AK47(), T72())
    soldier.fight()
    
    // 通过get获取特定武器
    println("First weapon: ${soldier[0]?.name}")
    println("Second weapon: ${soldier[1]?.name}")
}

执行结果

sql 复制代码
Weapon fire!
AK47 fire fire!
Weapon fire!
T72 fire fire!
First weapon: AK47
Second weapon: T72

💡 为什么这样组合这么强大?

  1. 灵活性vararg允许你传递任意数量的武器
  2. 便捷性get函数让你能像数组一样通过索引获取武器
  3. 类型安全 :通过泛型<T : Weapon>确保只能添加武器类型

🌟 实际应用场景

1. 通用数据结构

kotlin 复制代码
class DataContainer<T>(vararg items: T) {
    private val data = items.toList()
    
    operator fun get(index: Int): T {
        return data[index]
    }
    
    fun size(): Int {
        return data.size
    }
}

fun main() {
    val container = DataContainer("Apple", "Banana", "Cherry")
    println(container[0]) // Apple
    println(container.size()) // 3
}

2. 网络请求参数

kotlin 复制代码
fun fetchUrl(vararg urls: String) {
    // 处理多个URL
    urls.forEach { url ->
        println("Fetching $url")
    }
}

// 使用示例
fetchUrl("https://example.com", "https://example.org", "https://example.net")

3. 日志记录

kotlin 复制代码
fun log(vararg messages: String) {
    messages.forEach { message ->
        println("LOG: $message")
    }
}

// 使用示例
log("User logged in", "Session created", "Data loaded")

📌 重要注意事项

  1. vararg必须是最后一个参数

    kotlin 复制代码
    // 正确
    fun process(a: Int, vararg b: String)
    
    // 错误
    fun process(vararg a: String, b: Int) // 编译错误
  2. 不能直接传递数组

    kotlin 复制代码
    val array = arrayOf("a", "b", "c")
    // 下面代码会报错:Type mismatch: inferred type is Array<String> but String was expected
    process(array)
    
    // 正确做法:使用*操作符
    process(*array)
  3. get函数必须使用operator关键字

    kotlin 复制代码
    operator fun get(index: Int): T { ... } // 必须加operator

💡 小贴士

  1. 命名约定 :vararg参数通常使用itemsvaluesnumbers等描述性名称
  2. 类型推断:Kotlin会自动推断vararg参数的类型
  3. 性能考虑:vararg在内部会创建一个数组,对于大量数据可能有性能开销
  4. 替代方案:如果需要频繁使用,考虑使用集合类型(如List)代替vararg

🌈 一个有趣的练习

试试看,写一个ShoppingCart类,它能存储任意数量的商品,并通过get函数按索引获取:

kotlin 复制代码
class ShoppingCart<T>(vararg items: T) {
    private val itemsList = items.toList()
    
    operator fun get(index: Int): T {
        return itemsList[index]
    }
    
    fun add(item: T) {
        // 实际实现会添加到列表
        println("Added $item to cart")
    }
}

fun main() {
    val cart = ShoppingCart("Apple", "Banana", "Cherry")
    println("First item: ${cart[0]}")
    cart.add("Mango")
}

📚 总结

  • vararg:让函数接收任意数量的同类型参数
  • get:重载[]运算符,实现类似数组的索引访问
  • 组合使用 :通过operator fun get,可以像访问数组一样通过索引获取vararg参数

这种组合让Kotlin的代码既灵活又安全,是Kotlin语言中非常优雅的特性之一!你学会了吗?😊

需要我帮你解决什么实际问题,或者想了解更多Kotlin的高级特性吗?我很乐意继续和你探讨!

相关推荐
STCNXPARM4 小时前
Android camera之硬件架构
android·硬件架构·camera
2501_944525546 小时前
Flutter for OpenHarmony 个人理财管理App实战 - 支出分析页面
android·开发语言·前端·javascript·flutter
松☆7 小时前
Dart 核心语法精讲:从空安全到流程控制(3)
android·java·开发语言
_李小白9 小时前
【Android 美颜相机】第二十三天:GPUImageDarkenBlendFilter(变暗混合滤镜)
android·数码相机
小天源11 小时前
银河麒麟 V10(x86_64)离线安装 MySQL 8.0
android·mysql·adb·麒麟v10
2501_9159214311 小时前
傻瓜式 HTTPS 抓包,简单抓取iOS设备数据
android·网络协议·ios·小程序·https·uni-app·iphone
csj5013 小时前
安卓基础之《(20)—高级控件(2)列表类视图》
android
JMchen12313 小时前
Android计算摄影实战:多帧合成、HDR+与夜景算法深度剖析
android·经验分享·数码相机·算法·移动开发·android-studio
恋猫de小郭14 小时前
Flutter 在 Android 出现随机字体裁剪?其实是图层合并时的边界计算问题
android·flutter·ios
2501_9159184114 小时前
把 iOS 性能监控融入日常开发与测试流程的做法
android·ios·小程序·https·uni-app·iphone·webview