使用Groovy将字符串或字符串数组转换为列表

18

我有一个多选变量提交到控制器。多选的工作方式是,如果只选择了一个值,则传递为单个字符串,如果选择了多个值,则传递为字符串数组。我想保持处理简单,并将传递的值视为相同的。所以我想到的最好的方法是将其转换为List,如下所示:

def selectedValues = params.selectedValues

List valuelist = new ArrayList()

if(selectedValues instanceof String) {
    valuelist.add(selectedValues)
} else {
    valuelist = selectedValues as List
}

它可以工作,但我想知道是否有更巧妙的方法来做到这一点,也许可以用一行代码实现 :)

当然,如果我只是这样做:

List valuelist = selectedValues as List

如果只选择单个值,它将无法起作用,因为它会将其从24转换为[2,4]。

有什么想法吗?

3个回答

29
您可以使用"flatten"函数来实现此功能:
def toList(value) {
    [value].flatten().findAll { it != null }
}

assert( ["foo"] == toList("foo") )
assert( ["foo", "bar"] == toList(["foo", "bar"]) )
assert( [] == toList([]) )
assert( [] == toList(null) )

或者,如果您不想使用单独的方法,可以将其作为一个一行代码来完成:

[params.selectedValues].flatten().findAll{ it != null }

我个人会写两个方法,然后让类型系统自动处理:

def toList(String value) {
    return [value]
}

def toList(value) {
    value ?: []
}

assert( ["foo"] == toList("foo") )
assert( ["foo", "bar"] == toList(["foo", "bar"]) )
assert( [] == toList([]) )
assert( [] == toList(null) )

这样更高效,我认为更容易理解正在发生的事情。


1
.findAll { it != null } 更短的写法是 - null,它将从数组中删除所有的 null 条目。 - mmigdol

20
在最新版的Grails中,只需使用params.list('xxx')即可。

1
这实际上是该问题的更好解决方案,因为它更简单,因此更优雅。您不需要用 'flatten()' 来搞乱您的代码,也不需要使用方法重载等技巧。 - Tiago Farias

5

尝试这个:

def valueList = []
valueList = valueList + params?.selectedValues

更新: 根据您想要的空值情况,还有其他几个选择。正如Ted所指出的那样,上面的解决方案将在params?.selectedValues为空时返回[null],这可能不是您想要的。

// if you want null to return []
def valueList = [] + (params?.selectedValues ?: [])

或者

// if you want null to return null
def valueList = params?.selectedValues ? ([] + params?.selectedValues) : null

如果selectedValues为null,则该代码无法正常工作,但使用if?then:else运算符可以轻松解决:def valueList = params?. selectedValues? [] + params?. selectedValues:[]。 - Ted Naleid
按照我的解决方案,它会返回[null];按照你提出的方案,它将返回[];而Micor提出的解决方案,对于selectedValues == null 会返回null。不过你说得对,如果有可能存在空值,则这可能不是期望的行为。 - chrislatimer

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接