Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/visual-studio/8.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_Pattern Matching_Traits_Sealed - Fatal编程技术网

Scala:当模式匹配到密封特征时,编译器不会发出警告

Scala:当模式匹配到密封特征时,编译器不会发出警告,scala,pattern-matching,traits,sealed,Scala,Pattern Matching,Traits,Sealed,这里是一个片段。模式匹配时,编译器不会发出警告。你知道有什么解决办法吗 我希望编译器在忘记与SimpleExpr.Expr和OtherExpr.Expr进行模式匹配时发出警告。此结构允许我将两个表达式树共有的节点(如If)分解为因子 因为sealed是不可传递的,所以我不清楚缺少编译错误是否是一个bug 我注意到在匹配表达式中添加另一个case会导致编译器发出“无法访问代码”警告。以下是我对您的代码的修改版本: #!/usr/bin/env scala Demo.main(args) seal

这里是一个片段。模式匹配时,编译器不会发出警告。你知道有什么解决办法吗

我希望编译器在忘记与
SimpleExpr.Expr
OtherExpr.Expr
进行模式匹配时发出警告。此结构允许我将两个表达式树共有的节点(如
If
)分解为因子


因为
sealed
是不可传递的,所以我不清楚缺少编译错误是否是一个bug

我注意到在
匹配
表达式中添加另一个case会导致编译器发出“无法访问代码”警告。以下是我对您的代码的修改版本:

#!/usr/bin/env scala
Demo.main(args)

sealed trait Hierarchy {
  sealed trait Expr
}
trait If {
  this: Hierarchy =>
  case class If(cond: Expr, yes: Expr, no: Expr) extends Expr
}
trait Word {
  this: Hierarchy =>
  case class Word(name: String) extends Expr
}

object SimpleExpr extends Hierarchy with If with Word
//object OtherExpr extends Hierarchy with If with Integer

object Demo extends App {
  import SimpleExpr._
  def func(expr: Expr) = expr match {
    case If(cond, yes, no) => cond
    // compiler should emit warning
    case Word(name) => printf("word[%s]\n",name)
  }
  func(Word("yo!"))
}
以下是我运行它时得到的结果:

warning: unreachable code
case Word(name) => printf("word[%s]\n",name)
one warning found
word[yo!]
警告不正确,正在执行
无法访问的
代码

当注释掉
case Word
行时,我得到如下结果:

scala.MatchError: Word(yo!) (of class Main$$anon$1$Word$Word)
    at Main$$anon$1$Demo$.func(demo.sc:21)
但是,以下情况确实会发出所需的警告:

#!/usr/bin/env scala
Demo.main(args)

sealed trait Expr
case class Word(name: String) extends Expr
case class If(cond: Expr, yes: Expr, no: Expr) extends Expr

trait Hierarchy
trait IfExpr {
  this: Hierarchy =>
}
trait WordExpr {
  this: Hierarchy =>
}

object SimpleExpr extends Hierarchy with IfExpr with WordExpr
//object OtherExpr extends Hierarchy with If with Integer

object Demo extends App {
  import SimpleExpr._
  def func(expr: Expr) = expr match {
    case If(cond, yes, no) => cond
    // compiler should emit warning
    // case Word(name) => printf("word[%s]\n",name)
  }
  // func(Word("yo!"))
}
以下是我得到的警告:

demo.sc:22: warning: match may not be exhaustive.
It would fail on the following input: Word(_)
  def func(expr: Expr) = expr match {
                     ^

我终于找到了一个达到预期效果的解决方案:

trait Hierarchy {
  sealed trait Expr
  case class Unit() extends Expr
}
trait AddIf extends Hierarchy {
  case class If(cond: Expr) extends Expr
}
trait AddWord extends Hierarchy {
  case class Word(name: String) extends Expr
}
trait AddSymb extends Hierarchy {
  case class Symb(name: String) extends Expr
}


object AST1 extends Hierarchy with AddIf
object AST2 extends Hierarchy with AddSymb with AddIf


object TestMatch extends App {
  def match1(e: AST1.Expr) = e match {
    case AST1.If(cond) => 1
  }
  def match2(e: AST2.Expr) = e match {
    case AST2.If(cond) => 1
    case AST2.Unit() => 1
  }
}

那么,(为了确保)你同意这是一个bug吗?警告似乎是一个bug。另一个显然不是。我试图封闭等级制度,但仍然没有“封闭的行为”。你是怎么弄到的?谢谢你的兴趣和时间。我对你的答案投了赞成票。(我仍然在寻找一种方法来达到预期的效果,所以我还没有接受它……也许有人会有一个创造性的想法)我发现注释掉“case class Word”的定义不会导致编译错误,所以在层次结构中定义一个特征似乎并没有义务以任何方式实现类。请参阅我的修订答案,以获得可能满足您要求的版本。
trait Hierarchy {
  sealed trait Expr
  case class Unit() extends Expr
}
trait AddIf extends Hierarchy {
  case class If(cond: Expr) extends Expr
}
trait AddWord extends Hierarchy {
  case class Word(name: String) extends Expr
}
trait AddSymb extends Hierarchy {
  case class Symb(name: String) extends Expr
}


object AST1 extends Hierarchy with AddIf
object AST2 extends Hierarchy with AddSymb with AddIf


object TestMatch extends App {
  def match1(e: AST1.Expr) = e match {
    case AST1.If(cond) => 1
  }
  def match2(e: AST2.Expr) = e match {
    case AST2.If(cond) => 1
    case AST2.Unit() => 1
  }
}