Kotlin DSL 自动 add/generate 到 MutableList
Kotlin DSL automatically add/generate to MutableList
我一直在努力让 DSL 像这样工作。我想将 lambda 中的项目添加到 persons 中的 mutableList 中。有人可以帮忙吗?
persons {
Person("name")
Person("name second")
}
lambda 执行后的预期结果,所有这些项目将像这样放在 mutableList 中:
mutableListOf(Person("name"), Person("name second"))
与您使用的不完全一样,但应该可以使用类似
的东西
data class Person(var name: String? = null)
class Persons : ArrayList<Person>() {
fun person(block: Person.() -> Unit) {
val person = Person().apply(block)
add(person)
}
}
fun persons(block : Persons.() -> Unit): Persons = Persons().apply(block)
fun main() {
val personList = persons {
person {
name = "John"
}
person {
name = "Jane"
}
}
println(personList)
}
(这可以扩展为使用某种构建器模式以允许在数据中使用不可变值 class)
假设 Person
是:
data class Person(val name: String)
然后 Person("name")
行什么都不做——它只是声明了一个未使用的实例。 Person("name second")
做同样的事情(一般来说,因为它是 lambda 的最后一行,它作为 lambda expsession 的结果隐式返回,理论上,它可以稍后处理;无论如何,DSL 语法不会在一般情况)。
您不仅需要声明实例,还需要将它们添加到列表中。因此,您需要声明一些辅助函数(例如,person
,以接近所需的语法),这将在幕后执行此操作:
class Persons {
val delegate: MutableList<Person> = mutableListOf()
fun person(name: String, block: Person.() -> Unit = {}) {
delegate.add(Person(name).also(block))
}
}
fun persons(block: Persons.() -> Unit) = Persons().also(block).delegate.toList() //mutation was needed only during construction, afterwards consider preserving immutability
用法:
val persons: List<Person> = persons {
person("name")
person("name second")
}
我一直在努力让 DSL 像这样工作。我想将 lambda 中的项目添加到 persons 中的 mutableList 中。有人可以帮忙吗?
persons {
Person("name")
Person("name second")
}
lambda 执行后的预期结果,所有这些项目将像这样放在 mutableList 中:
mutableListOf(Person("name"), Person("name second"))
与您使用的不完全一样,但应该可以使用类似
的东西data class Person(var name: String? = null)
class Persons : ArrayList<Person>() {
fun person(block: Person.() -> Unit) {
val person = Person().apply(block)
add(person)
}
}
fun persons(block : Persons.() -> Unit): Persons = Persons().apply(block)
fun main() {
val personList = persons {
person {
name = "John"
}
person {
name = "Jane"
}
}
println(personList)
}
(这可以扩展为使用某种构建器模式以允许在数据中使用不可变值 class)
假设 Person
是:
data class Person(val name: String)
然后 Person("name")
行什么都不做——它只是声明了一个未使用的实例。 Person("name second")
做同样的事情(一般来说,因为它是 lambda 的最后一行,它作为 lambda expsession 的结果隐式返回,理论上,它可以稍后处理;无论如何,DSL 语法不会在一般情况)。
您不仅需要声明实例,还需要将它们添加到列表中。因此,您需要声明一些辅助函数(例如,person
,以接近所需的语法),这将在幕后执行此操作:
class Persons {
val delegate: MutableList<Person> = mutableListOf()
fun person(name: String, block: Person.() -> Unit = {}) {
delegate.add(Person(name).also(block))
}
}
fun persons(block: Persons.() -> Unit) = Persons().also(block).delegate.toList() //mutation was needed only during construction, afterwards consider preserving immutability
用法:
val persons: List<Person> = persons {
person("name")
person("name second")
}