我想链接一些Options
来计算最终值。很简单:
def compute(aOpt: Option[String], bOpt: Option[String],
cFun: (String, String) => Option[String]): Option[String] = {
for (a <- aOpt; b <- bOpt; c <- cFun(a, b)) yield a + b + c
}
但是我需要添加调试信息 - 记录丢失的数据。像下面的代码,它可以工作,但它有点笨拙:
def compute(aOpt: Option[String], bOpt: Option[String],
cFun: (String, String) => Option[String], logger: Logger): Option[String] = {
if (aOpt.isEmpty) {
logger.error("a is empty")
}
if (bOpt.isEmpty) {
logger.error("b is empty")
}
val cOpt = for ( a <- aOpt; b <- bOpt) yield cFun(a,b)
if (cOpt.isEmpty) {
logger.error("c is not found")
}
for (a <- aOpt; b <- bOpt; c <- cOpt) yield a + b + c
}
我正在寻找优雅和惯用的方法来实现它。
编辑:我改进了代码,因为在之前的版本中它有时会调用cFun
两次
答案 0 :(得分:3)
如果可以只记录第一个“空虚”,那么您可以为Option[T]
定义隐式助手类:
implicit class LogOption[T](opt: Option[T]){
def orLogError(msg: String)(implicit logger: Logger) = { // Require an implicit Logger
if(opt.isEmpty) logger.error(msg); opt // Always log as error
}
}
然后将你的理解写成:
for {
a <- aOpt orLogError "a is empty"
b <- bOpt orLogError "b is empty"
c <- cFun(a, b) orLogError "c is not found"
} yield a + b + c
答案 1 :(得分:0)
def compute(aOpt: Option[String],
bOpt: Option[String],
cFun: (String, String) => Option[String], logger: Logger): Option[String] = {
val optList = List((aOpt, "a"),
(bOpt, "b"),
(cFun(aOpt.getOrElse(""), bOpt.getOrElse("")), "c"))
optList.foreach(x => if(x._1.isEmpty) logger.error(x._2 + " is Empty"))
for (a <- aOpt; b <- bOpt; c <- cFun(a, b)) yield a + b + c
}
答案 2 :(得分:0)
@Federico Pellegatta回答让我满意 - 第一个错误对我来说已经足够了。但仅供参考,我提交了他的解决方案的修改,记录了所有错误:
pref=$(cut -d_ -f1-2 <<< "$s")