我正在处理一些第三方HTML,这是一种半结构化的标记文本(粗体,斜体等)。
以下是结构的简化示例:
<div>
<strong class="term">one</strong>
-
<b class="defs">
foo
<i class="pos">verb</i>
bar
<i class="pos">noun</i>
baz
<i class="pos">adjective</i>
blah
</b>
<br>
<strong class="term">two</strong>
... etc ...
</div>
事实上,我已经对它进行了一些处理,以使其成为这种形状。我可以处理HTML元素,,但我还没有弄清楚如何处理交错文本和<i>
元素。
我对解决方案感到满意,这个解决方案要么分拆&#34; defs&#34;围绕<i>
s,一个遍历各个部分的解决方案,等等。我宁愿不混合使用jQuery和&#34; raw&#34;由于浏览器特定的怪癖,DOM API调用,但我知道如果我无法避免它。从我的浅薄知识来看,jQuery对标记文本的支持并不像&#34;结构&#34; HTML ...
我错过了一些明显的东西吗?这似乎很难搜索......
事实证明,在现实世界数据中,文本运行且<i>
节点始终是交错的,但defs
中的第一个可能是一个,每个文本运行可以包含一个或多个实际文本节点。这意味着<i>
和文本运行不是匹配对。
好的解决方案可能是为每个文本运行添加标记,或者迭代,为每个<i>
做一件事,为每个文本运行做另一件事。我认为jQuery.contents()
一些节点类型检查必须是关键...
答案 0 :(得分:3)
您可以执行以下操作将所有文本检索到数组中
$(function(){
var json = $('.defs').contents().map(function(){
var text = $.trim($(this).text());
return text != "" ? text : null;
});
console.log(json);
});
演示: http://jsfiddle.net/joycse06/Z5AgL/
上面的代码为您提供了所有defs
以及textnode和i
的列表。
<强>更新强>
是的,您可以使用地图功能中的this.nodeName
或this.nodeType
进行节点类型或名称检查。 nodeType
的{{1}}为textnode
。例如在3
内添加此内容并检查
.map()
因此,对于此特定标记结构,您可以执行以下操作以检查它是console.log(this.nodeName,this.nodeType);
还是<i>
textnode
答案 1 :(得分:1)
如果您的结构始终如您所示,您可以这样做:
var defs = [];
var def = null;
var tokens = $('.defs').text().split('\n');
for (var i=0; i<tokens.length; i++) {
if (tokens[i].trim().length>0) {
if (def==null) {
def = {name:tokens[i]};
} else {
def.value = tokens[i];
defs.push(def);
def = null;
}
}
};
console.log(defs);
当然,你必须增加保护,或者根据你所拥有的内容进行充实,但你会得到你可以做的那种操作的精神。
另一个解决方案是将所有部分都用斜体($('.pos')
)来查找它们在$('.defs').text()
中的第一个位置(在最后一个提取的对之后的第一个位置)。