11

我希望看到使用http://anti-xml.org而不是 Scala XML 重写波纹管脚本。

这是第 10 章的节选。Scala 中的 Herding XML - http://ofps.oreilly.com/titles/9780596155957/HerdingXMLInScalaDSLs.html

// code-examples/XML/reading/pattern-matching-script.scala
import scala.xml._
val someXML =
 <sammich>
   <bread>wheat</bread>
   <meat>salami</meat>
   <condiments>
     <condiment expired="true">mayo</condiment>
     <condiment expired="false">mustard</condiment>
   </condiments>
</sammich>

someXML match {
 case <sammich>{ingredients @ _*}</sammich> => {
    for (cond @ <condiments>{_*}</condiments> <- ingredients)
      println("condiments: " + cond.text)
    }
}

谢谢

4

1 回答 1

6

我对antixml不熟悉,但是,由于没有其他答案,我会尝试一下

仅作记录,您的代码返回

  mayo
  mustard

更准确地说,字符串以 first 的结尾和开头之间的空格/换行符开始。蛋黄酱和芥末之间的空白是两种调味品之间的空白,芥末之后的空白是关闭之前的空白。

在antixml中,首先要做的似乎是转换你的,这很简单

val someAntiXml = someXML.anti

获得调味品部分很容易:

var condiments = someAntiXml \ 'condiments

然后必须提取文本。听起来这样做的方法是

condiments \\ text

但是\\ 不按顺序遍历结构,看起来像广度优先遍历。因此,略低于调味品的空白在元素中位于低于一级的蛋黄酱和芥末酱之前。

因此,这是检索文本的可能实现。也许有一种更标准的方法,但我没有找到。

def textOf(g: Group[Node]) : String = 
  g.toList.map{
    case Elem(_, _, _, _, children) => textOf(children) 
    case t: Text => t.text
    case c: CDATA => c.text 
    case _ => ""
  }.mkString

然后textOf(someAntiXml \ "condiments")给出预期的结果。

于 2011-08-06T15:54:43.080 回答