2016-09-12 4 views
2

TreeMap을 사용하고 있으며 다음 코드에서 이상하게 동작합니다. 여기 TreeMap 스칼라의 키와 반복

코드입니다 :

(0,1) 
(0,2) 
(1,3) 
(3,4) 
**** 
(0,2) 
(1,3) 
(3,4) 

왜 :

import scala.collection.immutable.TreeMap 
object TreeMapTest extends App{ 

    val mp = TreeMap((0,1) -> "a", (0,2) -> "b", (1,3) -> "c", (3,4) -> "f") 
    mp.keys.foreach(println) //A 
    println("****") 
    mp.map(x => x._1).foreach(println) //B 
} 

다음과 같이 같은 일을 인쇄해야 두 인쇄 라인 (A와 B)를 볼 수 있지만 결과이므로 여기서 일어나는거야? 흥미로운 점은 IDE도이 두 가지를 서로 바꾸어 사용할 수 있다고 생각하고 교체를 제안합니다.

+0

'키'의 순서가 문제라고 생각하지 않습니다. 두 번째 예제에서 첫 번째 키가 누락 된 것처럼 보입니다. – irundaia

+0

아, 이런. 감사. 그 질문에 그냥 오류라고 가정! –

답변

3

스칼라 컬렉션 라이브러리는 일반적으로 시작하는 컬렉션과 동일한 종류의 컬렉션을 반환하려고 시도하므로 일반적으로 val seq: Seq[Int] = ...; seq.map(...)Seq, val seq: List[Int] = ...; seq.map(...)List 등을 반환합니다. 항상 가능한 것은 아닙니다. 예 : StringChar의 컬렉션으로 간주되지만 "ab".map(x => x.toInt)은 분명히 String을 반환 할 수 없습니다. 마찬가지로 Map의 경우 : map이 아닌 쌍으로 된 각 쌍은 Map을 다시 가져올 수 없습니다. 각 쌍을 (Int, Int) 쌍으로 매핑하므로 스칼라는 Map[Int, Int]을 반환합니다. 따라서 (0, 1)(0, 2)을 모두 가져올 수 없습니다 : 중복 키가됩니다.

이 문제를 방지하려면지도를 Seq[((Int, Int), String)] (mp.toSeq.map(x => x._1) 또는 mp.keySet.toSeq)으로 변환하십시오.

+0

흥미롭게도 컴파일러가이 상황에 대한 경고를 던져서는 안됩니까? 사람들이 잘못 이해할 수있는 것일뿐입니다. – Omid

+0

의도적 인 상황과 어떻게 구분할 수 있습니까? 예 : map.map {case (k, v) => (k, v +1)}')? 분명히, Map # map은 제거 될 수 없다. 당신은 그 비난에 대해 논쟁하려고 할 수 있습니다,하지만 나는 성공을 기대하지 않을 것입니다. –