2017-01-13 1 views
3

HList에 관해서는 거의 읽을 수있는 문서가 없기 때문에 내가 찾을 수있는 대답은 우주 공간에서 나온다. 겸손한 스칼라 초보자를위한 것이다.Scala HList에서 요소를 읽는 방법?

Slick이 데이터베이스 행을 나타 내기 위해 일부를 자동 생성 할 수 있으므로 HLists가 발생했습니다. 그들은 slick.collection.heterogeneous.HList (형태가없는 ')입니다. 예 : 이러한 행의

type MyRow = HCons[Int,HCons[String,HCons[Option[String],HCons[Int,HCons[String,HCons[Int,HCons[Int,HCons[Option[Int],HCons[Option[Float],HCons[Option[Float],HCons[Option[String],HCons[Option[String],HCons[Boolean,HCons[Option[String],HCons[Option[String],HCons[Option[String],HCons[Option[String],HCons[Option[String],HCons[Option[Int],HCons[Option[Float],HCons[Option[Float],HCons[Option[Float],HCons[Option[String],HCons[Option[String],HNil]]]]]]]]]]]]]]]]]]]]]]]] 
def MyRow(a, b, c, ...): MyRow = a :: b :: c :: ... :: HNil 

지금 주어진 일, 나는 하나 개의 요소, 가능하면 입력을 읽을 필요가 것입니다. 나는 그렇게 할 수 없다. 나는 누군가가 내가 그 공룡에서 특정 값을 추출하는 방법을 설명시겠습니까

row(4) // error 
row._4 // error 
row.toList // elements are inferred as Any 
row match { case a :: b :: c :: x :: rest => x } // "Pattern type is incompatible. Expected MyRow." 
row match { case MyRow(_,_,_,_,_,x,...) => x } // is not a case class like other rows 
row match { HCons[Int,HCons[String,HCons[Option[String],HCons[Int,HCons[String, x]]]]] => x.head } // error 
row.tail.tail.tail.tail.head // well, is that really the way?? 

를 시도?

+0

......'공룡 '.... 당신은'HList'를 상당히 두려워하는 것 같습니다. –

+1

@SarveshKumarSingh는 모르는 사람의 성격을 반영하는 의견을 내보낼 필요가 없습니다. 그 의견을 삭제 해 줄 것을 제안해도 될까요? – maasg

답변

1

, 이것에 대해 나는 당신의 row(0) 조회를 기대할 수있는 방법

또는 ...은 HList API doc for apply에 따라 작동합니다. 다음은 Slick 3.1.1에서 사용한 예입니다.

scala> import slick.collection.heterogeneous._ 
import slick.collection.heterogeneous._ 

scala> import slick.collection.heterogeneous.syntax._ 
import slick.collection.heterogeneous.syntax._ 

scala> type MyRow = Int :: String :: HNil 
defined type alias MyRow 

scala> val row: MyRow = 1 :: "a" :: HNil 
row: MyRow = 1 :: a :: HNil 

scala> row(0) + 99 
res1: Int = 100 

scala> val a: String = row(1) 
a: String = a 

이것이 작동하지 않는 경우 표시되는 오류를 공유 할 수 있습니다.

+0

이 새로운 가져 오기를 시도했는데'row.head'의 형식이'Int'인데도'row (0)'의 형식은'Any'입니다. – JulienD

+0

오, IntellIJ는 오류 ("Any는 예상 유형 Int를 준수하지 않음")로 밑줄을 긋지 만 사실 실제로 컴파일됩니다. 나는 이것이 어떻게 가능한지 이해하지 못한다. – JulienD

+1

두 가지 :'row (0)'의 결과는 결국 'Int'인 유형 별칭이며 IntelliJ가 혼란 스러울 수 있습니다. 또한 IntelliJ의 혼란의 원천이 될 수있는 매크로를 알아 냈습니다. 몰라요 .-- (또한 'val n = 0; 행과 같은 런타임 값을 사용하는 경우 (n)''row (0)'과 같은 문자 그대로)'Any '로 끝날 것 같아요. –

0

단지 하나만 ... 으로 HList에 붙는 것보다 중요하지 않은 경우 ... 필요한 경우가 아니면 aliasMyRow으로 변경하지 마십시오.

그래서 .. 당신은 이것에 대해

val row = a :: b :: c :: ... :: HNil 

어떻게

했다?

val yourX = row match { case a :: b :: c :: x ::: rest => x } 

통지 ::: 대신의 말에 :: 그.

val yourX = row.tail.tail.tail.head 

// this may change a little if you had, 
def MyRow(a, b, c, ...): MyRow = a :: b :: c :: ... :: HNil 

val row = MyRow(a, b, c, ...) 

val yourX = row.asInstanceOf[HList].tail.tail.tail.head 
+0

Sbt는 "기호 ':::'를 (를) 해결할 수 없습니다."라고 말합니다. 두 번째 해결책은 제가 지금 사용하고있는 것입니다. 요소 12, 14, 15, 17, 26 및 27을 원한다고 상상해보십시오. 그러나 다른 해결책이 없다면, 저는 그것을 지키도록하겠습니다. – JulienD

+0

이 ":::"실제로 scaladocs에 있지만 패턴 매칭 작업을 할 수 없습니다. '.tail.tail.tail ... '대신에'.drop'을 사용하는 방법이 있어야합니다. 대답 해줘서 고마워. – JulienD

관련 문제