Scala中的空部分函数

Scala中的空部分函数,scala,partialfunction,Scala,Partialfunction,在我看来,分部函数的{case…=>…}语法至少需要一个case: scala> val pf: PartialFunction[String, String] = { case "a" => "b" } pf: PartialFunction[String,String] = <function1> scala> val pf: PartialFunction[String, String] = { } <console&

在我看来,分部函数的
{case…=>…}
语法至少需要一个
case

scala> val pf: PartialFunction[String, String] = { case "a" => "b" } 
pf: PartialFunction[String,String] = <function1>

scala> val pf: PartialFunction[String, String] = { }                
<console>:5: error: type mismatch;
 found   : Unit
 required: PartialFunction[String,String]
       val pf: PartialFunction[String, String] = { }
                                                 ^
scala>val-pf:PartialFunction[String,String]={case“a”=>“b”}
pf:PartialFunction[字符串,字符串]=
scala>val-pf:PartialFunction[String,String]={}
:5:错误:类型不匹配;
发现:单位
必需:PartialFunction[字符串,字符串]
val pf:PartialFunction[String,String]={}
^
那么,定义“空”部分函数的最佳方法是什么?有没有比“手动”覆盖
应用中定义更好的方法?

scala>def pfEmpty[a,B]=新的部分函数[a,B]{
scala> def pfEmpty[A, B] = new PartialFunction[A, B] {
     |   def apply(a: A): B = sys.error("Not supported")
     |   def isDefinedAt(a: A) = false
     | }
pfEmpty: [A, B]=> java.lang.Object with PartialFunction[A,B]

scala> val f = pfEmpty[String, String]
f: java.lang.Object with PartialFunction[String,String] = <function1>

scala> f.lift
res26: (String) => Option[String] = <function1>

scala> res26("Hola")
res27: Option[String] = None
|def apply(a:a):B=系统错误(“不支持”) |def isDefinedAt(a:a)=false | } pfEmpty:[A,B]=>java.lang.Object,带有PartialFunction[A,B] scala>val f=pfEmpty[字符串,字符串] f:java.lang.Object,带有PartialFunction[String,String]= scala>f.lift res26:(字符串)=>选项[字符串]= scala>res26(“Hola”) res27:选项[字符串]=无
正如@didierd在评论中所说的,由于参数的差异,单个实例可以覆盖所有可能的参数类型

scala> object Undefined extends PartialFunction[Any, Nothing] {
     |   def isDefinedAt(a: Any) = false
     |   def apply(a: Any): Nothing = sys.error("undefined")
     | }
defined module Undefined

scala> val f: PartialFunction[String, String] = Undefined
f: PartialFunction[String,String] = <function1>

scala> f.lift apply "Hola"
res29: Option[String] = None
scala>对象未定义扩展部分函数[Any,Nothing]{
|def isDefinedAt(a:Any)=false
|def apply(a:Any):Nothing=sys.error(“未定义”)
| }
已定义模块未定义
scala>val f:PartialFunction[String,String]=未定义
f:PartialFunction[字符串,字符串]=
scala>f.提升应用“Hola”
res29:选项[字符串]=无
解决方案(更像是一种黑客行为)是确保案例永远不会为真:
{case x if x!=x=>sys.error(“意外匹配”)}


简单的好奇,你为什么需要这样一个功能?

我能想到的最短的一个:

{ case _ if false => "" }

从每个人身上偷东西,可能是所有东西的混合:

val undefined : PartialFunction[Any, Nothing] = {case _ if false =>
  sys.error("undefined")
}

Map是一个PartialFunction,因此您可以执行以下操作:

val undefined: PartialFunction[Any, Nothing] = Map.empty

了解计划向scala库中添加一个空成员并了解其实现方式可能会很有趣:

自Scala 2.10以来,您可以使用:

val emptyPf = PartialFunction.empty[String, String]

@尼古拉斯:是的,定义一个为你做这件事的函数。(
pfEmpty
此处);)@尼古拉斯:老实说,当我读到这个问题时,我错过了那一行。谢谢你指出!我知道我的问题不满足问题中指定的约束条件,但无论如何,我把它留在这里,希望它可能对某些人有用。给定参数的差异,一个实例就可以解决所有问题:object Undefined[Any,Nothing]{…your impl…}我的帖子中有两个问号@missingfaktor对第一个问题给出了一个很好的答案,并在第二个问题上含蓄地说“据我所知不是这样的”。:-)+1.不应应用引发scala.MatchError异常?这就是应用未为输入定义的PF通常所做的。我有一个接受分部函数的API,我想为它提供一个未为任何参数定义的分部函数。在
=>
之后不需要一个
,它才能成为有效的
分部函数[String,String]
。如果是这样,那就有点不幸了,因为它被绑定到了
”的结果类型,不是吗?(似乎另一种选择是抛出新的RuntimeException()
,但这可能更难看。)你的想法是什么?@aioobe你会怎么做。我没有注意到PF的类型。将
更改为
null
(或任何其他?)是否会使其适用于所有可能的部分函数(而不仅仅是返回
字符串的函数)?@aioobe否。要使其普遍适用,您必须使用
error
或类似的方法,当它们返回时,
无任何内容
<代码>无
是所有事物的唯一子类型。
系统错误
有什么好处?它永远不会被执行。@aioobe:它有一个类型
Nothing
。一个类型为Nothing的更为独立的表达式,可以替换sys.error调用:未定义(未定义)。现在在
PartialFunction
伴随对象上定义了一个空的分部函数。这是一个老问题和老答案。当前的实现可以在那里找到:(l.246-259)实际上还有大量未被记录的
FSM.NullFunction
(它做同样的事情)。我现在正在添加文档。由于2.10
PartialFunction.empty可用