如果句点和尾注引用(上标)之间没有 space,则 Sub 无法找到长句
Sub fails to find long sentences if there is not a space between the period and endnote citations (superscripts)
我有一个简单的循环(如下),用于查找超过 30 个单词的句子。如果找到,它会在所选句子中添加一个评论框。它在测试中运行良好。然后我添加了一些测试尾注引用...但它找不到长句。
但是,只有在句点和引文上标之间没有space时才会失败。如果我添加 space,它会找到并完美运行。问题是,根据我在工作中必须遵循的风格指南,句号和引文之间不应该有 space。
This related Stack thread 讨论了在句号之后使用 space 来划定句子结尾的必要性。我 假设 space 必须紧接在句点之后,因为我的引用中有 space 像这样的 1, 2, 3
问题
如何找到句点+上标的实例(没有像这样的space --> This is a sentence.1, 2, 3)并添加一个space?理想情况下,我希望这发生在下面的循环中,这样我就可以在添加评论后删除 space。
Sub Comment_on_Long_Sentences ()
Dim iWords as Integer
iWords = 0
For Each MySent in ActiveDocument.Sentences
If MySent.Words.Count > iWords Then
MySent.Select
'find and delete space
ActiveDocument.Comments.Add Range:= Selection.Range, Text:= "Long Sentence: " & iWords & " words"
'put the space back
End if
Next MySent
End Sub
在尝试访问以上标字符结尾的句子时,VBA 中似乎存在问题。您的代码还存在未声明变量的问题,所以我一开始就不知道它是如何为您工作的。
按照 VBA 例程试试这个,它在我的环境中有效。另请注意,我发现段落中的第一个句子以及该句子以上标字符结尾时需要进行特殊处理。
Sub Comment_on_Long_Sentences()
Dim doc As word.Document, rng As word.Range, para As word.Paragraph
Dim i As Long
Set doc = ActiveDocument
For Each para In doc.Paragraphs
Debug.Print para.Range.Sentences.Count
For i = 1 To para.Range.Sentences.Count
Set rng = para.Range.Sentences(i)
If i = 1 And rng.Characters.First.Font.Superscript = True Then
rng.MoveStart word.WdUnits.wdSentence, Count:=-1
End If
If rng.words.Count > 30 Then
doc.Comments.Add Range:=rng, Text:="Long Sentence: " & rng.words.Count & " words"
End If
Next
Next
End Sub
这是一个替代解决方案。注意开始时的显式选项。将它放在每个模块的顶部是很好的 VBA 做法。
您遇到的问题很常见。然后找到一些东西而不是做一个替换,做一些其他与替换相关的事情。引文前加减空格的subs实现了这种模式,非常值得学习
如果您什么都不懂,那么在 VBA IDE 中,只需将光标放在相关关键字上,然后按 F1。这将调出相关的 MS 帮助页面。
Option explicit
Sub Comment_on_Long_Sentences()
Dim iWords As Integer
Dim my_sentence As Variant
iWords = 30
AddSpaceBeforeCitations
For Each my_sentence In ActiveDocument.Sentences
If my_sentence.Words.Count > iWords Then
my_sentence.Comments.Add Range:=my_sentence, Text:="Long Sentence: " & iWords & " words"
End If
Next my_sentence
RemoveSpaceBeforeCitations
End Sub
Sub AddSpaceBeforeCitations()
With ActiveDocument.Content
With .Find
.ClearFormatting
.Format = True
.Text = ""
.Wrap = wdFindStop
.Font.Superscript = True
.Execute
End With
Do While .Find.Found
With .Previous(unit:=wdCharacter, Count:=1).characters
If .Last.Text = "." Then
.Last.Text = ". "
End If
End With
.Collapse direction:=wdCollapseEnd
.Move unit:=wdCharacter, Count:=1
.Find.Execute
Loop
End With
End Sub
Sub RemoveSpaceBeforeCitations()
With ActiveDocument.Content
With .Find
.ClearFormatting
.Format = True
.Text = ""
.Wrap = wdFindStop
.Font.Superscript = True
.Execute
End With
Do While .Find.Found
With .Previous(unit:=wdCharacter, Count:=2).characters
If (.Last.Text = ".") Then
.Last.Next(unit:=wdCharacter, Count:=1).characters.Last.Text = vbNullString
End If
End With
.Collapse direction:=wdCollapseEnd
.Move unit:=wdCharacter, Count:=1
.Find.Execute
Loop
End With
End Sub
无论您采用何种方法,任何依赖于 VBA .Sentence 属性 或 .Word 属性 的代码都将产生不可靠的结果。那是因为 .Sentence 不知道什么是符合语法的句子,而 .Word 不知道什么是符合语法的词。例如,考虑以下内容:
先生。史密斯在 Dr. John's Grocery Store 花费了 1,234.56 美元,购买了 10.25 公斤土豆、10 公斤鳄梨和 15.1 公斤 Mrs. Green's Mt. Pleasant 澳洲坚果。
对你我来说,这算作一个 26 字的句子;对于 VBA,它算作 5 个句子,总共包含 45 个单词。要获得准确的字数统计,请使用 .ComputeStatistics(wdStatisticWords)。遗憾的是,句子没有 .ComputeStatistics(wdStatisticSentences) 等价物。
我有一个简单的循环(如下),用于查找超过 30 个单词的句子。如果找到,它会在所选句子中添加一个评论框。它在测试中运行良好。然后我添加了一些测试尾注引用...但它找不到长句。
但是,只有在句点和引文上标之间没有space时才会失败。如果我添加 space,它会找到并完美运行。问题是,根据我在工作中必须遵循的风格指南,句号和引文之间不应该有 space。
This related Stack thread 讨论了在句号之后使用 space 来划定句子结尾的必要性。我 假设 space 必须紧接在句点之后,因为我的引用中有 space 像这样的 1, 2, 3
问题
如何找到句点+上标的实例(没有像这样的space --> This is a sentence.1, 2, 3)并添加一个space?理想情况下,我希望这发生在下面的循环中,这样我就可以在添加评论后删除 space。
Sub Comment_on_Long_Sentences ()
Dim iWords as Integer
iWords = 0
For Each MySent in ActiveDocument.Sentences
If MySent.Words.Count > iWords Then
MySent.Select
'find and delete space
ActiveDocument.Comments.Add Range:= Selection.Range, Text:= "Long Sentence: " & iWords & " words"
'put the space back
End if
Next MySent
End Sub
在尝试访问以上标字符结尾的句子时,VBA 中似乎存在问题。您的代码还存在未声明变量的问题,所以我一开始就不知道它是如何为您工作的。
按照 VBA 例程试试这个,它在我的环境中有效。另请注意,我发现段落中的第一个句子以及该句子以上标字符结尾时需要进行特殊处理。
Sub Comment_on_Long_Sentences()
Dim doc As word.Document, rng As word.Range, para As word.Paragraph
Dim i As Long
Set doc = ActiveDocument
For Each para In doc.Paragraphs
Debug.Print para.Range.Sentences.Count
For i = 1 To para.Range.Sentences.Count
Set rng = para.Range.Sentences(i)
If i = 1 And rng.Characters.First.Font.Superscript = True Then
rng.MoveStart word.WdUnits.wdSentence, Count:=-1
End If
If rng.words.Count > 30 Then
doc.Comments.Add Range:=rng, Text:="Long Sentence: " & rng.words.Count & " words"
End If
Next
Next
End Sub
这是一个替代解决方案。注意开始时的显式选项。将它放在每个模块的顶部是很好的 VBA 做法。
您遇到的问题很常见。然后找到一些东西而不是做一个替换,做一些其他与替换相关的事情。引文前加减空格的subs实现了这种模式,非常值得学习
如果您什么都不懂,那么在 VBA IDE 中,只需将光标放在相关关键字上,然后按 F1。这将调出相关的 MS 帮助页面。
Option explicit
Sub Comment_on_Long_Sentences()
Dim iWords As Integer
Dim my_sentence As Variant
iWords = 30
AddSpaceBeforeCitations
For Each my_sentence In ActiveDocument.Sentences
If my_sentence.Words.Count > iWords Then
my_sentence.Comments.Add Range:=my_sentence, Text:="Long Sentence: " & iWords & " words"
End If
Next my_sentence
RemoveSpaceBeforeCitations
End Sub
Sub AddSpaceBeforeCitations()
With ActiveDocument.Content
With .Find
.ClearFormatting
.Format = True
.Text = ""
.Wrap = wdFindStop
.Font.Superscript = True
.Execute
End With
Do While .Find.Found
With .Previous(unit:=wdCharacter, Count:=1).characters
If .Last.Text = "." Then
.Last.Text = ". "
End If
End With
.Collapse direction:=wdCollapseEnd
.Move unit:=wdCharacter, Count:=1
.Find.Execute
Loop
End With
End Sub
Sub RemoveSpaceBeforeCitations()
With ActiveDocument.Content
With .Find
.ClearFormatting
.Format = True
.Text = ""
.Wrap = wdFindStop
.Font.Superscript = True
.Execute
End With
Do While .Find.Found
With .Previous(unit:=wdCharacter, Count:=2).characters
If (.Last.Text = ".") Then
.Last.Next(unit:=wdCharacter, Count:=1).characters.Last.Text = vbNullString
End If
End With
.Collapse direction:=wdCollapseEnd
.Move unit:=wdCharacter, Count:=1
.Find.Execute
Loop
End With
End Sub
无论您采用何种方法,任何依赖于 VBA .Sentence 属性 或 .Word 属性 的代码都将产生不可靠的结果。那是因为 .Sentence 不知道什么是符合语法的句子,而 .Word 不知道什么是符合语法的词。例如,考虑以下内容:
先生。史密斯在 Dr. John's Grocery Store 花费了 1,234.56 美元,购买了 10.25 公斤土豆、10 公斤鳄梨和 15.1 公斤 Mrs. Green's Mt. Pleasant 澳洲坚果。
对你我来说,这算作一个 26 字的句子;对于 VBA,它算作 5 个句子,总共包含 45 个单词。要获得准确的字数统计,请使用 .ComputeStatistics(wdStatisticWords)。遗憾的是,句子没有 .ComputeStatistics(wdStatisticSentences) 等价物。