Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/python-3.x/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
在Scala中创建任意的高级类型_Scala_Higher Kinded Types - Fatal编程技术网

在Scala中创建任意的高级类型

在Scala中创建任意的高级类型,scala,higher-kinded-types,Scala,Higher Kinded Types,从一开始我就不确定我是否有正确的方法来解决我的问题。我在这里寻找两个不同的答案: 这个问题的替代方案受到欢迎,但是 我想了解我如何才能使下面的例子起作用——或者我对更高级的类型遗漏了什么,这意味着这种方法是错误的 我有一些我希望动态(最终在运行时)添加不同属性的“东西”。例如 “文档”对象可能有地址属性。另一个“文件”的事情可能会发生 具有“收件人电子邮件地址”属性。第三个“文档”东西可能具有这两个属性 下面的代码显示了包含的(可能表示各种事物)和一个事物(其中之一) 它还包括两个HigherK

从一开始我就不确定我是否有正确的方法来解决我的问题。我在这里寻找两个不同的答案:

  • 这个问题的替代方案受到欢迎,但是
  • 我想了解我如何才能使下面的例子起作用——或者我对更高级的类型遗漏了什么,这意味着这种方法是错误的
  • 我有一些我希望动态(最终在运行时)添加不同属性的“东西”。例如 “文档”对象可能有地址属性。另一个“文件”的事情可能会发生 具有“收件人电子邮件地址”属性。第三个“文档”东西可能具有这两个属性

    下面的代码显示了包含的(可能表示各种事物)和一个事物(其中之一)

    它还包括两个HigherKindeType特性,这是我希望动态添加到所包含内容中的属性

    我不能创建一个“带有属性的任意类型”,我希望在ContainedOps类中这样做

    请帮我完成这个???零件

    package example
    
    import scala.language.higherKinds
    
    trait Contained[A]
    case class Thing(id: String) extends Contained[Thing]
    
    //case class Attribute(value: String) // needed ?
    
    trait WithAttribute[F[_]] {
      def attribute[A, B](fa: F[A])(f: A => B) : F[B]
    }
    
    trait WithAnotherAttribute[F[_]] {
      def anotherAttribute[A, B](fa: F[A])(f: A => B) : F[B]
    }
    
    object Contained {
    
      implicit class ContainedOps[A](c: Contained[A]) {
    
        type AWithAttribute = A with WithAttribute[Contained]
        def withAttribute(value: String): AWithAttribute = ???
    
        type AWithAnotherAttribute = A with WithAnotherAttribute[Contained]
        def withAnotherAttribute(value: String): AWithAnotherAttribute = ???
    
      }
    
    }
    
    object Example extends App {
    
      val thing = Thing("one")
      println(s"thing: $thing")
    
      val thingWithAttribute = thing.withAttribute("attributeValue")
      println(s"thingWithAttribute: $thingWithAttribute")
    
      val thingWithAnotherAttribute = thing.withAnotherAttribute("anotherAttributeValue")
      println(s"thingWithAnotherAttribute: $thingWithAnotherAttribute")
    
      val thingWithAttributeWithAnotherAttribute = thingWithAttribute.withAnotherAttribute("anotherAttributeValue")
      println(s"thingWithAttributeWithAnotherAttribute: $thingWithAttributeWithAnotherAttribute")
    
    }
    

    Scala类型是在编译时定义的,在运行时是静态的,因此“动态创建[]类型”是不可能的。

    您不能将动态结构与编译时保证混为一谈。或者重新思考您的问题,在编译时使一切都可用。或者使用运行时数据结构,例如,在本例中,为什么不简单地为您的属性使用
    Map[String,String]
    。谢谢Luis。我考虑过的一个选项与您的建议类似,但使用HMap,因为值可以是不同的类型(例如“Address”、“EMailAddress”),但这不太适合我的某些属性类型。某些属性(例如)只有在基础容器[A]属于特定类型时才能“添加”。有一些关于HKT的东西我没有点击-因为我不明白/为什么/上述方法没有(或不能)起作用。。。我认为你对动态/静态组合的看法是正确的,但我不想“排除它”,直到我更好地理解为什么我也这样做。再次感谢。如果我听起来粗鲁,请道歉(我觉得我的英语听起来粗鲁,因为它不是我的母语)。但HKT和你的问题有什么关系?HKT只不过是类型构造函数上的参数化类型(我也不明白为什么代码中需要它)。同样,一个
    HMap
    只在编译时才有意义,我认为您的问题并不像您所想的那样是动态的,因为您有适当的静态规则来确定属性是什么以及哪些规则决定了它们的行为。也许你应该重新制定这个问题(或打开一个新的问题),只关注设计。嗨,路易斯-你的评论没有粗鲁的地方-我欢迎他们。我的“动态”注释来自这样一个事实:用户(在运行时)可以选择将哪些属性添加到“东西”中。但是,用户可用的属性总是来自同一个“集合”,因此编译时解决方案可能是静态的。HKT可能不是根本问题的解决方案(如我最初所述)。。。但是,如果我向用户提供一个“文档”,那么他们会添加一个“电子邮件”属性。他们现在处理的文档的“类型”是“DocumentWithEMail”。我正在“玩”HKT,看看它是否有助于解决问题。根据您所描述的,我同意Luis的观点,您应该只对您不确定的属性使用选项。使用带有一些参数的case类作为类型选项。我希望这能解决你的问题。我的“动态”评论来自这样一个事实:用户(在运行时)可以选择将哪些属性添加到“东西”中。但是,用户可用的属性总是来自同一个“集合”,因此编译时解决方案可能是静态的。如果您的问题是关于动态地向对象添加属性,那么这应该是问题的标题。我回答了标题中的问题,因为这是其他人在浏览问题列表时所期望的。