문제

나는 다음과 같은 일부 sorthand 이:

Map rowToMap(row) {
    def rowMap = [:];
    row.columns.each{ rowMap[it.name] = it.val }
    return rowMap;
}

주어진 방법을 사용해 물건입니다,나는 기대를 할 수 있 다음과 같습니다.

Map rowToMap(row) {
    row.columns.collectMap{ [it.name,it.val] }
}

그러나 나는 아무것도 보지 않았는 문서에서...나는 뭔가?또는 나는 그냥 너무 게으른?

도움이 되었습니까?

해결책

나는 최근에 건너 왔어요 정확히 할 필요가있다:변환 목록으로 지도입니다.이 질문을 게시하기 전에 끝내 버전 1.7.9 나온다,그래서 방법 collectEntries 존재하지 않은 아직입니다.그것으로 정확하게 작동 collectMap 방법 는 제안:

Map rowToMap(row) {
    row.columns.collectEntries{[it.name, it.val]}
}

는 경우 어떤 이유로 당신은 이전에 그루비 버전 inject 방법도 사용할 수 있습(으로 제안 ).이것은 약간 수정 버전하는 단 하나의 식을 내밈(위해 단지 캐릭터의 저장!):

Map rowToMap(row) {
    row.columns.inject([:]) {map, col -> map << [(col.name): col.val]}
}

+ 연산자를 사용할 수도 있습신 <<.

다른 팁

Check out"주".진짜 프로그래밍 wonks call it"fold".

columns.inject([:]) { memo, entry ->
    memo[entry.name] = entry.val
    return memo
}

고,당신이 그것에있는 동안,당신은 아마을 정의하는 방법으로 카테고리가 오른쪽에 metaClass.는 방법을 정의할 수 있습니다 그것은 한 번에 대한 모든 컬렉션:

class PropertyMapCategory {
    static Map mapProperty(Collection c, String keyParam, String valParam) {
        return c.inject([:]) { memo, entry ->
            memo[entry[keyParam]] = entry[valParam]
            return memo
        }
    }
}

를 들어 사용:

use(PropertyMapCategory) {
    println columns.mapProperty('name', 'val')
}

groupBy 방법을 사용할 수 없을 때 이 질문을 묻?

또한,만약 당신이 사용하여 google 컬렉션(http://code.google.com/p/google-collections/),당신은 다음과 같이 할 수 있다:

  map = Maps.uniqueIndex(list, Functions.identity());

ok...나이 좀 더 많은 제 생각에 이것은 정말 멋진 메소드...

def collectMap = {Closure callback->
    def map = [:]
    delegate.each {
        def r = callback.call(it)
        map[r[0]] = r[1]
    }
    return map
}
ExpandoMetaClass.enableGlobally()
Collection.metaClass.collectMap = collectMap
Map.metaClass.collectMap = collectMap

지금 어떤 서브 클래스의 지도하거나 컬렉션가 이 방법은...

여기에서 내가 사용하는 그것을 반대하는 키/값에서 지도

[1:2, 3:4].collectMap{[it.value, it.key]} == [2:1, 4:3]

그리고 여기를 만드는 데 사용 지도서 목록

[1,2].collectMap{[it,it]} == [1:1, 2:2]

지금 나는 그냥 이로 클래스에 가져오라고한 내 응용 프로그램은 시작과 이 방법은 나의 코드입니다.

편집:

를 추가하는 방법을 모두 배열을...

Object[].metaClass.collectMap = collectMap

는 경우에 당신은 무엇이 필요한 간단한 키/값 쌍 다음 방법 collectEntries 충분해야 합니다.예를 들어

def names = ['Foo', 'Bar']
def firstAlphabetVsName = names.collectEntries {[it.charAt(0), it]} // [F:Foo, B:Bar]

하지만 당신이 원하는 구조와 비슷한 Multimap,에있는 여러 값을 키당,다음 사용하고 싶 groupBy 방법

def names = ['Foo', 'Bar', 'Fooey']
def firstAlphabetVsNames = names.groupBy { it.charAt(0) } // [F:[Foo, Fooey], B:[Bar]]

나는 아무것도 찾을 수 없습니다장에서...그러나 사용하여 ExpandoMetaClass 내가 작업을 수행 할 수 있습니다:

ArrayList.metaClass.collectMap = {Closure callback->
    def map = [:]
    delegate.each {
        def r = callback.call(it)
        map[r[0]] = r[1]
    }
    return map
}

이에 추가하 collectMap 방법을 모두 ArrayLists...나는 확실하지 않은 왜 그것을 추가하는 목록 또는 수집하지 않았다.나는 생각한 다른 질문은...그러나 이제는 내가 이것을 할 수 있는...

assert ["foo":"oof", "42":"24", "bar":"rab"] ==
            ["foo", "42", "bar"].collectMap { return [it, it.reverse()] }

목록에서 계산도 하나의 폐쇄...정확히 무엇을 찾고 있었습니다.

편집:그 이유는 내가 없을 추가하는 방법은 인터페이스 목록하고 수집하지 않았기 때문에 나는 이것:

List.metaClass.enableGlobally()

후에는 메소드 호출에 추가할 수 있습 방법을 인터페이스..이 경우 의미 내 collectMap 방법에서 작동 범위는 다음과 같다:

(0..2).collectMap{[it, it*2]}

을 산출 지도[0:0, 1:2, 2:4]

에 대해 무엇이 같은 뭔가?

// setup
class Pair { 
    String k; 
    String v; 
    public Pair(def k, def v) { this.k = k ; this.v = v; }
}
def list = [ new Pair('a', 'b'), new Pair('c', 'd') ]

// the idea
def map = [:]
list.each{ it -> map.putAt(it.k, it.v) }

// verify
println map['c']
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top