Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/string/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
String 搜索字符串在文本文件中出现的次数_String_Vbscript - Fatal编程技术网

String 搜索字符串在文本文件中出现的次数

String 搜索字符串在文本文件中出现的次数,string,vbscript,String,Vbscript,我正在尝试读取文本文件,并计算文本文件中出现短语/字符串(不是单词)的次数,但到目前为止,我得到的是: Const ForReading = 1 Set objFSO = CreateObject("Scripting.FileSystemObject") Set objFile = objFSO.OpenTextFile("D:\VBscript project\testing.txt", ForReading) strContents = objFile.ReadAll objFile.

我正在尝试读取文本文件,并计算文本文件中出现短语/字符串(不是单词)的次数,但到目前为止,我得到的是:

Const ForReading = 1

Set objFSO = CreateObject("Scripting.FileSystemObject")

Set objFile = objFSO.OpenTextFile("D:\VBscript project\testing.txt", ForReading)
strContents = objFile.ReadAll
objFile.Close

i = 0

arrLines = Split(strContents, "")

For Each strLine in arrLines
    If InStr(strLine, "hi there") Then
        i = i + 1
    End If
Next

WScript.Echo "Number of times word occurs: " & i

这只允许我计算一个单词出现的次数,当我试图调整它来计算词组时,这是不起作用的。

如果我正确理解了您的意思,并且您所要求的确实像它看起来一样简单,您可以将
“hi there”
字符串更改为一个参数。通过这种方式,您可以动态地告诉您的函数要查找什么

编辑:多亏了@omegastripes,我注意到我以前的代码中有一个缺陷,所以这是一个可行的

代码如下所示:

Sub yourSubName (pstrTextToCount)
    Const ForReading = 1
    Dim objFSO : Set objFSO = CreateObject("Scripting.FileSystemObject")
    Dim objFile : Set objFile = objFSO.OpenTextFile("D:\VBscript project\testing.txt", ForReading)
    Dim strContents : strContents = objFile.ReadAll
    objFile.Close

    ' You don't need these objects anymore, so release them
    Set objFile = Nothing
    Set objFSO = Nothing

    Dim intTextPosition : intTextPosition = 0
    Dim i : i = -1
    Do
      i = i + 1
      intTextPosition = InStr(intTextPosition + 1, strContents, pstrTextToCount)
    Loop While (intTextPosition > 0)

    Wscript.Echo "Number of times '" & pstrTextToCount & "' occurs: " & i
End Sub
我假设您的
Sub
只会这样做,这就是为什么我将其包含在
Sub
End Sub
语句中。您可以添加所需的任何其他编码,但只需记住在
的签名上添加所需的参数即可


PS:作为一种良好的做法,请始终
Dim
您的变量,并释放
Set objName=Nothing
不再需要的对象的内存。请考虑以下示例:

strPath = "D:\VBscript project\testing.txt"
strPhrase = "hi there"

strContent = ReadTextFile(strPath, 0)
arrContent = Split(strContent, strPhrase)

MsgBox "Number of times phrase occurs: " & UBound(arrContent)

Function ReadTextFile(strPath, lngFormat)
    ' lngFormat -2 - System default, -1 - Unicode, 0 - ASCII
    With CreateObject("Scripting.FileSystemObject").OpenTextFile(strPath, 1, False, lngFormat)
        ReadTextFile = ""
        If Not .AtEndOfStream Then ReadTextFile = .ReadAll
        .Close
    End With
End Function

请注意,基于拆分的方法是区分大小写的。

这里有一个使用正则表达式的版本,因此您可以指定搜索是否需要区分大小写。 出于测试目的,我使用脚本本身的内容作为输入

Dim path, phrase, content
path    = Wscript.ScriptFullName
phrase  = "hi there\^$*+?{}.()|[]"
content = CreateObject("Scripting.FileSystemObject").OpenTextFile(path).ReadAll

Function NumberOfPhrasesInString(phrase, text, IgnoreCase)
  Dim regexpr, matches
  Set regexpr = New RegExp
  phrase = RegExEscape(phrase)
  With regexpr
    .Pattern = phrase
    .Global  = True
    .IgnoreCase = IgnoreCase
    Set matches = .Execute(text)
  End With
  NumberOfPhrasesInString = matches.count
End Function

Function RegExEscape(str)
  Dim special
  RegExEscape = str
  special = "\^$*+?{.()|[]"
  For i=1 To Len(special)
    RegExEscape = replace(RegExEscape, Mid(special, i, 1), "\" & Mid(special, i, 1))
  Next
End Function

Wscript.Echo "Number of times phrase occurs: " & NumberOfPhrasesInString(phrase, content, false)
作为奖励,因为我在这里切换到Ruby,所以这个版本

path    = __FILE__ # the path to this script for test purposes
phrase  = 'HI THERE \ ^ $ * + ? { . ( | ['
puts phrase
content = File.read path

def number_of_phrases_in_string(phrase, text, ignoreCase=false )
  escaped = Regexp.escape(phrase)
  text.scan(Regexp.new(escaped, ignoreCase)).count.to_s 
end

puts "Number of times phrase occurs: " + number_of_phrases_in_string(phrase, content, true)
或者在一行中

puts File.read(__FILE__).scan(Regexp.new(Regexp.escape(phrase), true)).count

最后一行中的true定义大小写敏感度

Split(strContents,“”)
是无用的,因为它返回唯一的元素。感谢@omegastripes,分隔符实际上应该是
vbCrLf
。那么,如果一个字符串包含
pstrexttocount
文本e。G两次,它能正确地计算它们吗?正确到一个点。您和@omegastripes方法都只计算出现在一行上的短语。他们会跳过跨越多行的短语(例如,当两个单词之间有新行时)。这种情况可以通过在搜索匹配项之前用单个空格替换所有空格来解决。@Ansgar Wiechers,我同意你的观点,但这也可能取决于OP的意图。如果他/她想考虑单词计数,即使它之间有一个换行符,那么就需要替换空白,但是如果他想只计算同一行中出现的一个特定的单词序列,那么我相信两个答案都会做“替换”行>代码>短语=“Hy-Wield\”/代码> <代码>短语=“C:\Windows\System32”@omegastripes:这是一个简单的例子,特殊字符需要转义,在Ruby中使用.escape,应该必须搜索Vbscript,但考虑到当前出现的
\^$*+?{(|124;[
模式中的字符将导致意外的结果。在我看来,你要么修复错误,要么在回答中指出此特定功能。没问题,我编辑了所有三个版本以处理特殊字符。它再次显示了Ruby的强大功能,在保持可读性的同时保持代码简洁。@omegastripes:使用了错误的代码我猜是源代码,使用一个转义字符,也可以使用“C:\Windows\System32”,thnx
strPath = "D:\VBscript project\testing.txt"
strPhrase = "hi there"

strContent = ReadTextFile(strPath, 0)
arrContent = Split(strContent, strPhrase)

MsgBox "Number of times phrase occurs: " & UBound(arrContent)

Function ReadTextFile(strPath, lngFormat)
    ' lngFormat -2 - System default, -1 - Unicode, 0 - ASCII
    With CreateObject("Scripting.FileSystemObject").OpenTextFile(strPath, 1, False, lngFormat)
        ReadTextFile = ""
        If Not .AtEndOfStream Then ReadTextFile = .ReadAll
        .Close
    End With
End Function