我有超过100个文本文件,我必须计算每个文件的行数。 Column A
列出文件名,位于E1
中指定的文件夹中。有几个文件有超过100万行,导致脚本运行的时间非常长。
Sub counter()
Dim fso As New FileSystemObject
Dim ts As TextStream
Dim longtext As String
Dim lines As Variant
Dim GoToNum As Integer
Dim Start As Integer
GoToNum = 2
Start = 3
Do Until IsEmpty(Cells(Start, 1))
GoToNum = GoToNum + 1
Start = Start + 1
Loop
For i = 3 To GoToNum
If Cells(i, 2).Value <= Cells(2, 5).Value Then
ConOrg = Cells(1, 4).Value & "\" & Cells(i, 1).Value
Set ts = fso.OpenTextFile(ConOrg, ForReading, False)
longtext = ts.ReadAll
ts.Close
lines = Split(longtext, vbLf)
Cells(i, 3) = UBound(lines) - LBound(lines) - 1
End If
Next i
End Sub
如何获取最后一行的数字(来自文本文件)以避免逐行计数?
答案 0 :(得分:6)
40 MB文件(170万行)
- CountLF
= 25.2秒
- CountLines
= 2.1秒
14个B档(6行)x 10,000次
- CountLF
= 1.3秒
- CountLines
= 18.9秒
Function countLF(fName As String) As Long
Dim st As String
Open fName For Input As #1: st = Input(LOF(1), 1): Close #1
countLF = Len(st) - Len(Replace(st, vbLf, "")) + 1
End Function
使用示例:
Debug.Print countLF("c:\test.txt")
Function countLines(fName As String) As Long
countLines = CreateObject("Scripting.FileSystemObject").OpenTextFile(fName, 8, True).Line
End Function
使用示例:
Debug.Print countLines("c:\test.txt")
更多基准测试: (2500个小文本文件)
二进制访问/获取(4.32s)Kill = 1.17s。 。 。打开F进行二进制访问读取为#1:ReDim ...获取#1 ,,, bytes
线路输入/线路输入(4.44s)Kill = 1.11s。 。 。打开F输入为#iFile ...行输入#1,st
Early Bind / ReuseObj (5.25s)Del = 1.12s。 。 。设置o = New Scripting.FileSystemObject&#39;:st = o.OpenTextFile(F).ReadAll()
Early Bind / FreshObj (11.98s)Del = 1.35s。 。 。设置o = New Scripting.FileSystemObject&#39;:st = o.OpenTextFile(F).ReadAll()
LateBind / ReuseObj (6.25s)Del = 1.47s。 。 。设置o = CreateObject(&#34; Scripting.FileSystemObject&#34;)
LateBind / FreshObj (13.59s)Del = 2.29s。 。 。使用CreateObject(&#34; Scripting.FileSystemObject&#34;)
答案 1 :(得分:1)
尝试使用此功能。它使用FileSystemObject
。应该比读取整个文件更快并将其拆分为单行。灵感来自Hey, Scripting guy
Function countLines(fName As String) As Long
Const ForReading = 1
Dim objFSO As Object, objTextFile As Object
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objTextFile = objFSO.OpenTextFile(fName, ForReading)
objTextFile.ReadAll
countLines = objTextFile.Line
End Function
答案 2 :(得分:1)
另一种方法是使用Power Query(获取和转换数据):
let
Source = Folder.Files("C:\Users\me\MyFolder"),
#"Filtered Rows" = Table.SelectRows(Source, each [Extension] = ".txt"),
#"Added Row Count" = Table.AddColumn(#"Filtered Rows", "Rows In File", each Table.RowCount(Table.FromColumns({Lines.FromBinary([Content])})), Int64.Type),
#"Removed Columns" = Table.SelectColumns(#"Added Row Count",{"Name", "Rows In File"})
in
#"Removed Columns"
这非常快。
答案 3 :(得分:-1)
我认为你不能用一种方法阅读最后一行。
Do While fso.AtEndOfStream <> True
fso.SkipLine
Loop
lines = fso.Line-1
这样的事情会不会更快?