[SCALA] 지도 별 키에 컬렉션을 돌려 스칼라 가장 좋은 방법은?
SCALA지도 별 키에 컬렉션을 돌려 스칼라 가장 좋은 방법은?
내가 타입 T의 컬렉션 C를 가지고 T에 p 속성이있는 경우 (유형 P, 말의), 맵별로 추출 키를 할 수있는 가장 좋은 방법은 무엇입니까?
val c: Collection[T]
val m: Map[P, T]
한 가지 방법은 다음과 같다 :
m = new HashMap[P, T]
c foreach { t => m add (t.getP, t) }
하지만 지금은 변경 가능한지도가 필요합니다. 은 1 개 라인의 내가 불변의지도로 끝날 정도로이 일을 더 좋은 방법이 있나요? (물론 나는 자바에서와 마찬가지로 나는 간단한 라이브러리 유틸리티로 위를 돌 수 있었다, 그러나 나는 스칼라 필요가 없다고 생각한다)
해결법
-
==============================
1.당신이 사용할 수있는
당신이 사용할 수있는
c map (t => t.getP -> t) toMap
그러나이 2 개 순회 필요하다는 인식.
-
==============================
2.당신은 튜플의 변수 번호와지도를 구성 할 수 있습니다. 변수 인수로 결과를 변환 _ * 트릭 : 그래서를 사용하여 다음 튜플의 집합으로 변환하기 위해 컬렉션지도 방법을 사용합니다.
당신은 튜플의 변수 번호와지도를 구성 할 수 있습니다. 변수 인수로 결과를 변환 _ * 트릭 : 그래서를 사용하여 다음 튜플의 집합으로 변환하기 위해 컬렉션지도 방법을 사용합니다.
scala> val list = List("this", "maps", "string", "to", "length") map {s => (s, s.length)} list: List[(java.lang.String, Int)] = List((this,4), (maps,4), (string,6), (to,2), (length,6)) scala> val list = List("this", "is", "a", "bunch", "of", "strings") list: List[java.lang.String] = List(this, is, a, bunch, of, strings) scala> val string2Length = Map(list map {s => (s, s.length)} : _*) string2Length: scala.collection.immutable.Map[java.lang.String,Int] = Map(strings -> 7, of -> 2, bunch -> 5, a -> 1, is -> 2, this -> 4)
-
==============================
3.@ 제임스 Iry의 용액에 더하여, 배를 사용하여 이러한 작업을 수행하는 것도 가능하다. 나는이 솔루션은 빠르게 튜플 방법 (적은 쓰레기 object의 작성)보다 약간 것으로 의심 :
@ 제임스 Iry의 용액에 더하여, 배를 사용하여 이러한 작업을 수행하는 것도 가능하다. 나는이 솔루션은 빠르게 튜플 방법 (적은 쓰레기 object의 작성)보다 약간 것으로 의심 :
val list = List("this", "maps", "string", "to", "length") val map = list.foldLeft(Map[String, Int]()) { (m, s) => m(s) = s.length }
-
==============================
4.이것은 다음과 같이 수집을 접음으로써 불변 단일 통과로 구현 될 수있다.
이것은 다음과 같이 수집을 접음으로써 불변 단일 통과로 구현 될 수있다.
val map = c.foldLeft(Map[P, T]()) { (m, t) => m + (t.getP -> t) }
불변 맵에 추가하는 추가 항목을 가진 새로운 불변지도를 리턴하고이 값이 스크롤 동작을 통해 어큐뮬레이터로서 작용하기 때문에 상기 용액을 작동한다.
여기에 트레이드 오프는 그 효율성에 비해 코드의 단순함이다. 그래서, 큰 컬렉션에 대해,이 방법은지도 toMap인가 2- 순회 구현을 사용하는 것보다 더 적합 할 수있다.
-
==============================
5.또 다른 해결책 (모든 종류의 작동하지 않을 수 있습니다)
또 다른 해결책 (모든 종류의 작동하지 않을 수 있습니다)
import scala.collection.breakOut val m:Map[P, T] = c.map(t => (t.getP, t))(breakOut)
이 여기에 중간 목록의 생성, 더 많은 정보를 피할 수 : 스칼라 2.8 브레이크 아웃
-
==============================
6.당신이 달성하려고하는 것은 조금 정의되지 않습니다. 무엇 C에서 두 개 이상의 항목이 동일한 페이지를 공유하는 경우? 어떤 항목이지도에서 해당 페이지에 매핑 할 것인가?
당신이 달성하려고하는 것은 조금 정의되지 않습니다. 무엇 C에서 두 개 이상의 항목이 동일한 페이지를 공유하는 경우? 어떤 항목이지도에서 해당 페이지에 매핑 할 것인가?
이보고의보다 정확한 방법은 p와 그것을 가지고 모든 C 항목 사이의지도를 산출한다 :
val m: Map[P, Collection[T]]
이것은 쉽게 GROUPBY을 달성 할 수있다 :
val m: Map[P, Collection[T]] = c.groupBy(t => t.p)
당신은 여전히 원래지도를 원하는 경우, 예를 들어, 그것을있는 첫 번째 t에 페이지를 매핑 할 수 있습니다 :
val m: Map[P, T] = c.groupBy(t => t.p) map { case (p, ts) => p -> ts.head }
-
==============================
7.이것은 아마도 매핑 목록을 설정하는 가장 효율적인 방법은 아니지만 호출하는 코드를 읽기 수 있습니다. 나는 목록에 mapBy 방법을 추가하는 암시 적 변환을 사용 :
이것은 아마도 매핑 목록을 설정하는 가장 효율적인 방법은 아니지만 호출하는 코드를 읽기 수 있습니다. 나는 목록에 mapBy 방법을 추가하는 암시 적 변환을 사용 :
implicit def list2ListWithMapBy[T](list: List[T]): ListWithMapBy[T] = { new ListWithMapBy(list) } class ListWithMapBy[V](list: List[V]){ def mapBy[K](keyFunc: V => K) = { list.map(a => keyFunc(a) -> a).toMap } }
코드 예제를 호출 :
val list = List("A", "AA", "AAA") list.mapBy(_.length) //Map(1 -> A, 2 -> AA, 3 -> AAA)
참고 때문에 암시 적 변환의 발신자 코드는 수입 스칼라의 implicitConversions 할 필요가있다.
-
==============================
8.
c map (_.getP) zip c
잘 작동하고 매우 intuitiv입니다
-
==============================
9.어떻게 우편 및 toMap 사용에 대한?
어떻게 우편 및 toMap 사용에 대한?
myList.zip(myList.map(_.length)).toMap
-
==============================
10.무엇의 가치를 들어, 여기에 그 일을 두 가지 의미가 가지 방법이 있습니다 :
무엇의 가치를 들어, 여기에 그 일을 두 가지 의미가 가지 방법이 있습니다 :
scala> case class Foo(bar: Int) defined class Foo scala> import scalaz._, Scalaz._ import scalaz._ import Scalaz._ scala> val c = Vector(Foo(9), Foo(11)) c: scala.collection.immutable.Vector[Foo] = Vector(Foo(9), Foo(11)) scala> c.map(((_: Foo).bar) &&& identity).toMap res30: scala.collection.immutable.Map[Int,Foo] = Map(9 -> Foo(9), 11 -> Foo(11)) scala> c.map(((_: Foo).bar) >>= (Pair.apply[Int, Foo] _).curried).toMap res31: scala.collection.immutable.Map[Int,Foo] = Map(9 -> Foo(9), 11 -> Foo(11))
-
==============================
11.이것은 나를 위해 작동합니다 :
이것은 나를 위해 작동합니다 :
val personsMap = persons.foldLeft(scala.collection.mutable.Map[Int, PersonDTO]()) { (m, p) => m(p.id) = p; m }
지도는 변경 가능해야하고,지도는지도를 반환하지 않는 가변지도에 추가 이후 반환되어야합니다.
-
==============================
12.컬렉션 사용지도는 () toMap에 따라
컬렉션 사용지도는 () toMap에 따라
val map = list.map(e => (e, e.length)).toMap
from https://stackoverflow.com/questions/674639/scala-best-way-of-turning-a-collection-into-a-map-by-key by cc-by-sa and MIT license
'SCALA' 카테고리의 다른 글
[SCALA] 플레이 프레임 워크 및 스칼라와 IntelliJ를 사용하는 방법 (0) | 2019.11.13 |
---|---|
[SCALA] 어떻게 스칼라 컬렉션 맵 작업에서 올바른 모음 형식을 반환 할 수 있습니다? (0) | 2019.11.13 |
[SCALA] 스칼라의 "마법"기능 목록 (0) | 2019.11.13 |
[SCALA] 어떻게 스칼라의 방법을 프로파일 링하는? (0) | 2019.11.13 |
[SCALA] 스칼라가 명시 적으로 의존하는 유형을 지원하지 않는 이유 모든 이유? (0) | 2019.11.13 |