Kotlin中如何向listof()创建的列表添加元素?
问题分析与解决办法
核心问题
listOf<Coordinate>()创建的是不可变List,Kotlin里不可变集合的所有"修改"方法(比如plus())都不会改变原集合,而是返回一个包含新元素的新集合。你调用coordinate.plus(...)后没有把返回的新集合赋值回coordinate,所以原列表始终是空的。
解决办法
方案1:改用可变列表(推荐)
把初始化代码换成mutableListOf(),它返回的是MutableList,支持直接修改集合内容,用add()方法添加元素即可:
// 初始化可变列表 var coordinate = mutableListOf<Coordinate>() val databaseReference = FirebaseDatabase.getInstance().getReference("polygon").child("coordinate") databaseReference.addListenerForSingleValueEvent(object: ValueEventListener { override fun onDataChange(snapshot: DataSnapshot) { if (snapshot.exists()) { // 优化遍历:直接遍历子节点,不用依赖索引命名 for (childSnapshot in snapshot.children) { val latitude = childSnapshot.child("latitude").getValue(Double::class.java) ?: continue val longitude = childSnapshot.child("longitude").getValue(Double::class.java) ?: continue coordinate.add(Coordinate(longitude, latitude)) } } } override fun onCancelled(error: DatabaseError) { // 可添加错误处理,比如打印异常信息 error.toException().printStackTrace() } })
方案2:继续使用不可变List(不推荐循环场景)
如果一定要用不可变List,每次调用plus()后需要把返回的新列表重新赋值给coordinate,但这种方式每次循环都会创建新列表,性能较差:
var coordinate = listOf<Coordinate>() // ... Firebase监听代码 override fun onDataChange(snapshot: DataSnapshot) { if (snapshot.exists()) { for (childSnapshot in snapshot.children) { val latitude = childSnapshot.child("latitude").getValue(Double::class.java) ?: continue val longitude = childSnapshot.child("longitude").getValue(Double::class.java) ?: continue // 重新赋值新列表 coordinate = coordinate.plus(Coordinate(longitude, latitude)) } } }
额外优化点
- 不要依赖
coordinate1、coordinate2这种带索引的节点命名,直接遍历snapshot.children更可靠,避免节点数量变化或索引不连续导致的错误。 - 用
getValue(Double::class.java)直接获取Double类型,比先转String再转Double更安全,避免类型转换异常。 - 添加空值判断(
?: continue),防止某个节点缺少latitude/longitude时崩溃。
内容的提问来源于stack exchange,提问作者Tommy
相关产品推荐
相关产品推荐

