标签: shapeless

键入无形HList内容的推断

这个例子很简单.

我有一组像这样的类:

case class KeyMapping[KeyType](k:KeyType)

class WrappedMapping[KeyType](m:T forSome {type T <: KeyMapping[KeyType]}) {
  val k:KeyType = ???
}
Run Code Online (Sandbox Code Playgroud)

在以下代码中,正确推断了类型:

 val w = new WrappedMapping(KeyMapping("key"))

 //The statement below gives the correct error
 //type mismatch; 
 //  found : w.k.type (with underlying type String)  required: Nothing
 //val test1:Nothing = w.k
Run Code Online (Sandbox Code Playgroud)

我不知道如何正确推断以下类型:

class Mappings[KeyType, L <: HList](mappings:L) {
  val k:KeyType = ???
}

val m = new Mappings(KeyMapping("key1") :: KeyMapping("key2") :: HNil)

// should not compile, k should be of type String
val test2:Nothing …
Run Code Online (Sandbox Code Playgroud)

scala hlist shapeless

4
推荐指数
1
解决办法
544
查看次数

无形镜片的想法

我尝试使用版本2.0.0的shapless镜头scala 2.10.3我有类似于这个的代码:

import shapeless._
case class A(map: Map[String, String])
case class B(a: A)
val mapLens = lens[B] >> 'a >> 'map 
Run Code Online (Sandbox Code Playgroud)

理念中的感染类型mapLens

AnyRef with Lens[B, Nothing] {val gen: LabelledGeneric.Aux[Nothing, ::[record.FieldType[Witness.Lt[Symbol]#T, Nothing], Nothing]]}
Run Code Online (Sandbox Code Playgroud)

所以如果我想改变B实例的值

mapLens.set(b)(b.a.map + ("foo" -> "bar"))
Run Code Online (Sandbox Code Playgroud)

我收到类型不匹配错误.如何解决这个问题?

PS 这里有一个使用无定形镜片的例子.这lens[Person].address.street是怎么回事?我的意思是编译器如何允许我们在lense类的实例上调用case类的方法?因为在LenseExamples对象中使用了>>运算符

编辑 已在REPL中尝试过并且有效.Idea说它

could not find implicit value for evidence parameter of type shapeless.LabelledGeneric[B]{type Repr = Out0}
Run Code Online (Sandbox Code Playgroud)

同样的抱怨发出了争吵

scala intellij-idea shapeless

4
推荐指数
1
解决办法
728
查看次数

Scala中类型不相等的证据

有没有办法约束一个方法,只有两种类型被证明相等才有意义?

trait Something[A, B] {
  // I can only be called if type A is the same as type B
  def ifEqual(implicit ev: A =:= B)

  // Now I cannot be called if type A is proven to be the same as type B
  def ifNotEqual(implicit ev: A ??? B)
}
Run Code Online (Sandbox Code Playgroud)

types scala implicits shapeless

4
推荐指数
1
解决办法
1015
查看次数

在使用无形类型不等式时,如何自定义Scala模糊隐式错误

def typeSafeSum[T <: Nat, W <: Nat, R <: Nat](x: T, y: W)
         (implicit sum: Sum.Aux[T, W, R], error: R =:!= _7) = x

typeSafeSum(_3, _4) //compilation error, ambiguous implicit found.
Run Code Online (Sandbox Code Playgroud)

我不认为错误信息"模糊隐含发现"是友好的,我怎么能自定义它说"2 NAT值的总和不应该等于7"

提前谢谢了

scala shapeless

4
推荐指数
1
解决办法
1379
查看次数

如何将元素追加到HList

我正在尝试下面的课程

import shapeless._
import syntax.std.tuple._

class TestedClass[HL](nodes: HL) {

    def addElement[T, OUT](clause: HL => T) = {
        new TestedClass[OUT](nodes :+ clause(nodes))
    }
}
Run Code Online (Sandbox Code Playgroud)

显然这个片段没有编译.我不知道如何将新的元组nodes :+ clause(nodes)类型绑定到OUT.我想要实现的目标如下:

scala> val step1 = new TestedClass[(Int)](1)
res1: TestedClass[(Int)]

scala> val step2 = step1.addElement(nodes => 2.0)
res1: TestedClass[(Int, Double)]
Run Code Online (Sandbox Code Playgroud)

Scala有可能吗?

scala shapeless

4
推荐指数
1
解决办法
804
查看次数

矢量任何无形的HList

有没有办法将Any类型的矢量转换为无形HList(productelement)

val frame = Vector(Vector(1,"a","b",false),Vector(2,"y","z",false),Vector(3,"p","q",true))

frame.map(_.hlisted) or frame.map(_.productElements)
Run Code Online (Sandbox Code Playgroud)

我试图转换为以下结构

List[Int :: String :: String :: Boolean :: HNil](1 :: a :: b :: false :: HNil, 2 :: y :: z :: false :: HNil, 3 :: p :: q :: true :: HNil)
Run Code Online (Sandbox Code Playgroud)

基于Shapless Migration指南,可以使用Typed Tuples

https://github.com/milessabin/shapeless/wiki/Migration-guide:-shapeless-1.2.4-to-2.0.0#productelements-is-the-new-name-for-hlisted

import shapeless._
import syntax.std.product._  // New import

scala> (23, "foo", true).productElements // was '.hlisted'
res0: Int :: String :: HNil = 23 :: foo :: true :: HNil
Run Code Online (Sandbox Code Playgroud)

这是可能的非类型向量或矢量 - >类型元组 - …

scala scalaz scala-collections scala-2.10 shapeless

4
推荐指数
1
解决办法
249
查看次数

使用Scalaz(或Shapeless)为每个子类创建Monoids

是否有可能为每个子类创建幺半群?例如,

package currency 

final case class GBP[A: Monoid](amount: A)

object Implicits {
  implicit class CurrencyOps[A: Monoid](a: A) {
    def GBP = currency.GBP(a)
  }

  implicit def gbpMonoid[A: Monoid]: Monoid[GBP[A]] = new Monoid[GBP[A]] {
    override def zero =
      GBP(Monoid[A].zero)

    override def append(f1: GBP[A], f2: => GBP[A]): GBP[A] =
      GBP(Semigroup[A].append(f1.amount, f2.amount))
  }
}

test("GBP support plus") {
  1.GBP |+| 2.GBP shouldBe 3.GBP // passed
}
Run Code Online (Sandbox Code Playgroud)

我想补充的代表更多的案例类的货币(例如USD,EUR..)

sealed trait Currency
final case class GBP[A: Monoid](amount: A) extends Currency …
Run Code Online (Sandbox Code Playgroud)

scala scalaz shapeless

4
推荐指数
1
解决办法
334
查看次数

无形的案例类转换

我使用shapeless进行case类转换,我有一个2个案例类:

import shapeless._

case class Foo(id: Int, name: String)
case class Bar(id: Int, name: String, price: Double)

val fooGen = Generic[Foo]
val barGen = Generic[Bar]

val foo = Foo(1, "foo")
val fooRepr = fooGen.to(foo)
val additional = fooRepr :+ 1.0
val bar = barGen.from(additional)
Run Code Online (Sandbox Code Playgroud)

这工作正常,但当我尝试将Bar转换为Foo时

fooGen.from(barGen.to(bar))
Run Code Online (Sandbox Code Playgroud)

我收到一个错误:

found   : main.barGen.Repr
[error]     (which expands to)  shapeless.::[Int,shapeless.::    [String,shapeless.::[Double,shapeless.HNil]]]
[error]  required: main.fooGen.Repr
[error]     (which expands to)  shapeless.::[Int,shapeless.::[String,shapeless.HNil]]
[error]   println(fooGen.from(barGen.to(bar)))    
Run Code Online (Sandbox Code Playgroud)

是否有可能将一个案例类转换为更多字段而不是另一个案例类?

scala shapeless

4
推荐指数
1
解决办法
1884
查看次数

Type参数中`::`的含义?

看看Travis Brown关于Type类和泛型派生的优秀博客文章,我看到以下方法:

  implicit def hconsParser[H: Parser, T <: HList: Parser]: Parser[H :: T] =           
   new Parser[H :: T] {
    def apply(s: String): Option[H :: T] = s.split(",").toList match {
      case cell +: rest => for {
        head <- implicitly[Parser[H]].apply(cell)
        tail <- implicitly[Parser[T]].apply(rest.mkString(","))
      } yield head :: tail
    }
  }
Run Code Online (Sandbox Code Playgroud)

什么意思H :: TParser[H :: T]

另外,这case cell +: rest是如何处理s输入apply为空的情况?

scala shapeless

4
推荐指数
1
解决办法
87
查看次数

什么时候空HList不是HList?

在学习无形的同时,我想知道为什么这不能编译:

def someHList[H <: HList]: H = HNil
Run Code Online (Sandbox Code Playgroud)

既然HNil对象扩展了扩展HList的HNil特征?

在trait中定义一个方法的正确方法是什么,它返回一些HList,它只在扩展类中实现?

我想做类似以下的事情:

trait Parent {
  def someHList[H <: HList]: H
}

object Child1 extends Parent {
  def someHList[H <: HList] = HNil
}

object Child2 extends Parent {
  def someHList[H <: HList] = 1 :: "two" :: HNil
}
Run Code Online (Sandbox Code Playgroud)

任何建议表示赞赏.谢谢!

编辑

详细阐述,因为我意识到我在原始问题中未说明的内容:

1.)希望不必H在每个实现类中明确指定,而是推断它(在调用站点?).

2.)我想在父特征中使用HNil作为默认实现,可以选择在子类中重写.我的例子应该是:

trait Parent {
  def someHList[H <: HList]: H = HNil
}

object Child extends Parent {
  override def someHList[H <: HList] = 1 :: "two" …
Run Code Online (Sandbox Code Playgroud)

scala shapeless

4
推荐指数
1
解决办法
161
查看次数