feat: export core Hermes skills
This commit is contained in:
@@ -0,0 +1,65 @@
|
||||
# tracked_replace 被 DEL 元素打断(2026-06-26 CT维保合同-香花桥实证)
|
||||
|
||||
## 症状
|
||||
|
||||
`tracked_replace(old, new)` 对跨 DEL 元素的文本静默失败(不报错但也不修改)。
|
||||
|
||||
## 根因
|
||||
|
||||
当匹配文本被拆成多个 run,且中间夹着 `<w:del>` 元素时,`tracked_replace` 无法跨元素边界匹配完整字符串。
|
||||
|
||||
## 实证
|
||||
|
||||
**场景**:原文"一 年"(中间有空格),需改为"一年"。
|
||||
|
||||
实际 XML 结构:
|
||||
```xml
|
||||
<w:r><w:t>一</w:t></w:r>
|
||||
<w:del><w:r><w:delText> </w:delText></w:r></w:del>
|
||||
<w:r><w:t>年</w:t></w:r>
|
||||
```
|
||||
|
||||
`tracked_replace("一 年", "一年")` 无法匹配("一 年" 不连续存在于任何单一 run 中)。
|
||||
|
||||
## 修法
|
||||
|
||||
直接 zipfile+lxml 操作,移除 DEL 元素:
|
||||
|
||||
```python
|
||||
for elem in list(paragraph):
|
||||
if elem.tag.split('}')[-1] == 'del':
|
||||
for t in elem.iter():
|
||||
if t.tag == f'{{{W}}}delText' and t.text == ' ':
|
||||
paragraph.remove(elem)
|
||||
break
|
||||
```
|
||||
|
||||
## 同类变体:INS 需插入在 DEL 之后
|
||||
|
||||
**场景**:原文"与济损失"("与"为错字),上一轮已将"与"包进 DEL,但未补 INS "经"。
|
||||
|
||||
实际 XML 结构:
|
||||
```xml
|
||||
<w:del><w:r><w:delText>与</w:delText></w:r></w:del>
|
||||
<w:r><w:t>济损失的...</w:t></w:r>
|
||||
```
|
||||
|
||||
`tracked_replace("与济损失", "经济损失")` 静默失败("与"在 DEL 内)。
|
||||
|
||||
**修法**:zipfile+lxml 在 DEL 元素后插入 INS:
|
||||
```python
|
||||
ins = etree.SubElement(paragraph, f'{{{W}}}ins')
|
||||
ins.set(f'{{{W}}}id', str(new_id))
|
||||
ins.set(f'{{{W}}}author', 'WB')
|
||||
ins.set(f'{{{W}}}date', date_str)
|
||||
del_elem.addnext(ins) # INS 紧跟在 DEL 之后
|
||||
|
||||
r = etree.SubElement(ins, f'{{{W}}}r')
|
||||
r.append(copy.deepcopy(ref_rPr)) # 从同级 run 克隆 rPr
|
||||
t = etree.SubElement(r, f'{{{W}}}t')
|
||||
t.text = '经'
|
||||
```
|
||||
|
||||
## 判别
|
||||
|
||||
改前先遍历目标段落子元素,看是否有 `w:del` 或 `w:ins` 元素分割了匹配文本。有则不用 `tracked_replace`,改用 zipfile+lxml 直接操作。
|
||||
Reference in New Issue
Block a user