有什么方法可以简化以下内容?或者用另一个函数减少样板代码?
scala> val ns = <foo><bar id="1"><tag>one</tag><tag>uno</tag></bar><bar id="2"><tag>two</tag><tag>dos</tag></bar></foo>
ns: scala.xml.Elem = <foo><bar id="1"><tag>one</tag><tag>uno</tag></bar><bar id="2"><tag>two</tag><tag>dos</tag></bar></foo>
scala> (ns \\ "bar" filterNot{_ \\ "@id" find { _.text == "1" } isEmpty}) \\ "tag"
res0: scala.xml.NodeSeq = NodeSeq(<tag>one</tag>, <tag>uno</tag>)
答案 0 :(得分:16)
我只能找到一个小改进,find
/ isEmpty
测试可以替换为exists
:
(ns \\ "bar" filter { _ \\ "@id" exists (_.text == "1") }) \\ "tag"
澄清评论后编辑:
这是一个非常好的主意!试试这个尺寸:
import xml._
implicit def richNodeSeq(ns: NodeSeq) = new {
def \@(attribMatch: (String, String => Boolean)): NodeSeq =
ns filter { _ \\ ("@" + attribMatch._1) exists (s => attribMatch._2(s.text)) }
}
ns \\ "bar" \@ ("id", _ == "1") \\ "tag"
我使用谓词而不是硬编码属性值比较。
答案 1 :(得分:0)
最好的方法是定义隐式类:
object XmlE {
implicit class XmlE(val xml: NodeSeq) extends AnyVal {
def \@(attr: (String, String => Boolean)): NodeSeq = {
xml filter {
_ \ ("@" + attr._1) exists (s => attr._2(s.text))
}
}
}
}
然后在另一个类中使用它:
import XmlE._
.....