您现在的位置是:首页 > 文章详情

scala中trait和abstract class在隐式转换中的区别

日期:2021-06-09点击:432

说半天还不如看一点代码更清楚问题之所在:

 object ImplicitObject3 { def main(args: Array[String]): Unit = { def sum[A](xs:List[A])(implicit st:SubTemplate[A]):A = { if(xs.isEmpty) st.unit else st.add(xs.head,sum(xs.tail)) } implicit object SubTemplateImplicitIntValue extends SubTemplate[Int] { override def unit: Int = 0 override def add(x: Int, y: Int): Int = x + y } implicit object SubTemplateImplicitStringVlaue extends SubTemplate[String] { override def unit: String = "" override def add(x: String, y: String): String = x + y } println(sum(List(1,2,3,4,5))) println(sum(List("abc","efg","hijk"))) } } trait Template[A] { def add(x:A,y:A):A } trait SubTemplate[A] extends Template[A] { def unit:A }

编译正确,执行时:在类加载器加载时出现异常。但是将二个trait放在object ImplicitObject3中,不管是放在main的前面还是后面都执行OK:

 object ImplicitObject3 { trait Template[A] { def add(x:A,y:A):A } trait SubTemplate[A] extends Template[A] { def unit:A } def main(args: Array[String]): Unit = { def sum[A](xs:List[A])(implicit st:SubTemplate[A]):A = { if(xs.isEmpty) st.unit else st.add(xs.head,sum(xs.tail)) } implicit object SubTemplateImplicitIntValue extends SubTemplate[Int] { override def unit: Int = 0 override def add(x: Int, y: Int): Int = x + y } implicit object SubTemplateImplicitStringVlaue extends SubTemplate[String] { override def unit: String = "" override def add(x: String, y: String): String = x + y } println(sum(List(1,2,3,4,5))) println(sum(List("abc","efg","hijk"))) } } 

如果将二个trait改为abstract class形式,定义在object ImplicitObject3之外执行也OK:

 object ImplicitObject3 { def main(args: Array[String]): Unit = { def sum[A](xs:List[A])(implicit st:SubTemplate[A]):A = { if(xs.isEmpty) st.unit else st.add(xs.head,sum(xs.tail)) } implicit object SubTemplateImplicitIntValue extends SubTemplate[Int] { override def unit: Int = 0 override def add(x: Int, y: Int): Int = x + y } implicit object SubTemplateImplicitStringVlaue extends SubTemplate[String] { override def unit: String = "" override def add(x: String, y: String): String = x + y } println(sum(List(1,2,3,4,5))) println(sum(List("abc","efg","hijk"))) } } abstract class Template[A] { def add(x:A,y:A):A } abstract class SubTemplate[A] extends Template[A] { def unit:A }

为什么会有这样的现象,原因是什么呢???????????????????????

当我在object ImplicitObject3外面定义二个trait之外,还在二个trait同级定义了一个继承自SubTemplate[A]的abstract class类,同时将main中二个implicit object继承的父改为这个抽象类,则一切都OK了。这种情况下,实验OK,其实原因好理解:

 object ImplicitObject3 { def main(args: Array[String]): Unit = { def sum[A](xs:List[A])(implicit st:SubTemplate[A]):A = { if(xs.isEmpty) st.unit else st.add(xs.head,sum(xs.tail)) } implicit object SubTemplateImplicitIntValue extends abstractTemplate[Int] { override def unit: Int = 0 override def add(x: Int, y: Int): Int = x + y } implicit object SubTemplateImplicitStringVlaue extends abstractTemplate[String] { override def unit: String = "" override def add(x: String, y: String): String = x + y } println(sum(List(1,2,3,4,5))) println(sum(List("abc","efg","hijk"))) } } trait Template[A] { def add(x:A,y:A):A } trait SubTemplate[A] extends Template[A] { def unit:A } abstract class abstractTemplate[A] extends SubTemplate[A]

有一次无意中,我将二个trait放在另一个单独的scala文件中,然后我编译工程然后调试,不成功。鬼使神差地在main的最开头import SubTemplate一次,居然成功了。我将磁盘上所有class文件都删除了再编译工程却又不成功。然后再去掉import,单独编译那个scala文件,再编译工程却又成功执行代码了。总结来看:这是由于IDEA造成class文件与源代码不一致的原因

原文链接:https://my.oschina.net/u/2963604/blog/5074058
关注公众号

低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。

持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。

转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。

文章评论

共有0条评论来说两句吧...

文章二维码

扫描即可查看该文章

点击排行

推荐阅读

最新文章