我遇到了一个问题:
是否可以将regexp用作hashmap中的键? 例如:
def unitsMap=[
(~/(?i).*ABC.*nM.*/):'AAA',
(~/(?i).*DEF.*nM.*/):'DDD'
]
println unitsH3HashMap['ABC (122344345P)']
当然,返回null值。
祝你好运
答案 0 :(得分:3)
不,但你可以在开关中使用它:
def unitsMap(key) {
switch(key) {
case ~/(?i).*ABC.*/: return 'AAA'
case ~/(?i).*DEF.*/: return 'DDD'
}
}
println unitsMap('ABC (122344345P)')
答案 1 :(得分:0)
为了获得你想要的东西,你必须编写自己的Map实现,它使用模式匹配来执行getAt,putAt,contains等。但是,在我看来,在这种情况下查找的算法复杂性总是 O(n)。与HashMap( O(0))或TreeMap( O(log n))相比并不是很好。
@tim_yates的解决方案解决了所提出问题的原始轮廓,但不允许您动态添加新密钥(案例),就像您原来想要的代码一样。如果在飞行中改变你的地图"对你来说并不重要,那么你应该绝对使用他的解决方案(我现在赞同它现在给它+1)。如果没有,你可以调整他的代码来生成和调用一个可以做你想做的Map的脚本。
这个脚本:
// generate unitMapper
def generateUnitMapper(baseMap) {
def script = '''{ key ->
switch (key) {
'''
script += baseMap.collect { k, v ->
""" case ~/${k}/: return '${v}'
"""
}.join("")
script += ''' default: return null
}
}
'''
}
// notice this map is just using the regular expression STRINGS as keys,
// not the PATTERN objects from the original poster's code
def starterMap = [
/(?i).*ABC.*[\dA-Z]+.*/:'AAA',
/(?i).*DEF.*[\dA-Z]+.*/:'DDD'
]
def closureScript = generateUnitMapper(starterMap)
def unitsClosure = Eval.me(closureScript)
println closureScript
println unitsClosure('ABC (122344345P)')
println()
// regenerate map and closure and rerun
def changedMap = [ /ABC .*/:'000' ] + starterMap
closureScript = generateUnitMapper(changedMap)
unitsClosure = Eval.me(closureScript)
println closureScript
println unitsClosure('ABC (122344345P)')
产生此输出:
{ key ->
switch (key) {
case ~/(?i).*ABC.*[\dA-Z]+.*/: return 'AAA'
case ~/(?i).*DEF.*[\dA-Z]+.*/: return 'DDD'
default: return null
}
}
AAA
{ key ->
switch (key) {
case ~/ABC .*/: return '000'
case ~/(?i).*ABC.*[\dA-Z]+.*/: return 'AAA'
case ~/(?i).*DEF.*[\dA-Z]+.*/: return 'DDD'
default: return null
}
}
000