问题描述
背景
在 XHTML 文档中将直引号转换为卷曲引号和撇号。给定带有直引号("
和 '
)的文档,执行一些预处理以将直引号转换为其卷曲的语义等价物(“
、”
、 ‘
、’
和 '
)。通常,卷曲字符 ’
用于结束单引号(’
)和撇号('
),但这会丢失语义 em> 意思,我想通过使用实体来保留它——以便随后翻译成 TeX(例如,\quote{outer \quote{we’re inside quotes} outer}
)。因此:
Markdown -> XHTML (straight) -> XHTML (curled) -> TeX
代码使用了 Java 的内置文档对象模型 (DOM) 类。
问题
调用 Node
的 setTextContent
方法将对任何 & 符号进行双重编码,导致:
“I reckon,I'm 'bout dat.”
“Elizabeth Davenport;” she said ‘Elizabeth’ to be dignified,“and really my father owns the place.”
而不是:
“I reckon,I'm 'bout dat.”
“Elizabeth Davenport;” she said ‘Elizabeth’ to be dignified,“and really my father owns the place.”
通过设置处理指令来禁用和启用似乎不起作用。
代码
这是walk
一棵树的代码:
public static void walk(
final Document document,final String xpath,final Consumer<Node> consumer ) {
assert document != null;
assert consumer != null;
try {
final var expr = lookupXPathExpression( xpath );
final var nodes = (NodeList) expr.evaluate( document,NODESET );
if( nodes != null ) {
for( int i = 0,len = nodes.getLength(); i < len; i++ ) {
consumer.accept( nodes.item( i ) );
}
}
} catch( final Exception ex ) {
clue( ex );
}
}
这是用卷曲等价物替换引号的代码:
walk(
xhtml,"//*[normalize-space( text() ) != '']",node -> node.setTextContent( sConverter.apply( node.getTextContent() ) )
);
其中 xhtml
是 Document
和 sConverter
卷曲引号。
问题
如何指示 DOM 接受 '
和朋友而不重新编码&符号?
相关
半相关问题:
- How to disable/avoid Ampersand-Escaping in Java-XML?
- Disable automatic ampersand escaping in XML?
- XML DOM setTextContent
- Java XML Parsing: Avoid entity reference resolution
- https://stackoverflow.com/a/36097922/59087
解决方法
更改预处理以将直引号替换为 Unicode 字符,而不是无效的 XML 实体。这些实体由 HTML 定义,不是有效的 XML。
-
from django.core.exceptions import ValidationError class OrderLine(models.Model): order = models.ForeignKeyField( Order,on_delete=models.CASCADE ) loading_date = models.DateField() def clean(self): if self.loading_date < self.order.order_date: raise ValidationError('Can not load before ordering') return super().clean()
应该是“
或“
,如果写成 Java 文字 -
\u201C
应该是”
或”
,如果写成 Java 文字 -
\u201D
应该是‘
或‘
,如果写成 Java 文字 -
\u2018
应该是’
或’
,如果写成 Java 文字 -
\u2019
应该是'
XML 处理器可以随意地将字符和字符实体视为可互换的,因此尝试使用字符实体来表示语义是注定要失败的。
我会改用标记。我怀疑自定义处理指令是“秘密”添加语义的好方法:
<text>"She told me,'Don't forget the bread.'"</text>
会变成:
<text><?q?>“She told me,<?q?>‘Don’t forget the bread.<?q?>’<?q?>”</text>
其中 <?q?>
处理指令是一个信号,表明以下代码点具有作为引号的语义。
当然,如果需要,您可以拥有多个自定义处理指令:
<text><?quote-start?>“She told me,<?quote-start?>‘Don't forget the bread.<?quote-end?>’<?quote-end?>”</text>
就其价值而言,XHTML defines its own <quote>
element 可以处理这种确切情况。
(常规 HTML has a <q>
element 语义相似,但也告诉浏览器自动呈现引号,这意味着使用 <q>
的 HTML 文档不得包含自己的引号。)