基于Scala约束的类型和文字
我在想是否可以在
Scala中定义像NegativeNumber这样的类型.此类型将表示负数,编译器将检查它与Ints,Strings等类似.
val x: NegativeNumber = -34 val y: NegativeNumber = 34 // should not compile 同样: val s: ContainsHello = "hello world" val s: ContainsHello = "foo bar" // this should not compile either 我可以像其他类型一样使用这些类型,例如: def myFunc(x: ContainsHello): Unit = println(s"$x contains hello") 这些约束类型可以由临时类型(Int,String)支持. 是否可以实现这些类型(可能使用宏)? 自定义文字怎么样? val neg = -34n //neg is of type NegativeNumber because of the suffix val pos = 34n // compile error 解决方法
不幸的是,这不是你在编译时可以轻易检查的东西.好吧 – 至少不是因为你没有限制你的类型的操作.如果您的目标只是检查数字文字是否为非零,您可以轻松编写一个检查此属性的宏.但是,我认为证明负面文字确实是消极的,没有任何好处.
问题不在于Scala的限制 – 它具有非常强大的类型系统 – 但事实上(在一个相当复杂的程序中)你无法静态地知道每个可能的状态.但是,您可以尝试过度使用所有可能状态的集合. 让我们考虑引入只能表示负数的类型NegativeNumber的示例.为简单起见,我们只定义了一个操作:plus. 假设您只允许添加多个NegativeNumber,那么类型系统可用于保证每个NegativeNumber确实是负数.但这似乎是非常有限的,所以一个有用的例子肯定会允许我们至少添加一个NegativeNumber和一个通用的Int. 如果你有一个表达式val z:NegativeNumber = plus(x,y),你不能静态地知道x和y的值(也许它们是由函数返回的).你怎么知道(静态地)z是负数? 解决问题的方法是引入Abstract Interpretation,它必须在程序的表示上运行(源代码,抽象语法树,……). 例如,您可以使用以下元素在数字上定义格: >顶部:所有数字 订购Top> (,– )>底部. 然后,您需要为操作定义语义.采用交换方法加上我们的例子: > plus(Bottom,something)总是Bottom,因为你无法使用无效数字来计算 问题是 > plus – 将是Top,因为您不知道它是正数还是负数. 因此,为了保持静态,您必须采取保守的方法并禁止这样的操作. 有more sophisticated numerical domains但最终,它们都遭遇同样的问题:它们代表了对实际程序状态的过度逼近. 我说问题类似于整数溢出/下溢:通常,您不能静态地知道操作是否出现溢出 – 您只能在运行时知道这一点. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |