【问题标题】:Batch file to count lines per file and save in txt批处理文件以计算每个文件的行数并保存在 txt
【发布时间】:2017-12-12 20:14:58
【问题描述】:

我一直在尝试创建一个批处理文件,该文件将计算几个 csv 文件中的行数并将其输出到 txt 文件中。我已经设法弄清楚如何让批处理文件计算行数并放入一个文本文件,但我找不到一种方法让它给出文件的名称以及文件中有多少行这样..

file1.csv 100
文件 2.csv 112

我所能做的就是要么从一个文件中获取行,要么从所有 csv 文件中添加行并给我一个组合数字。

这是我尝试作为批处理基础的代码..

@echo off
cls
setlocal EnableDelayedExpansion
set "cmd=findstr /R /N "^^" file.txt | find /C ":""
    for /f %%a in ('!cmd!') do set number=%%a
echo %number% >>list.txt

我从这里找到它不是我的代码 How to count no of lines in text file and store the value into a variable using batch script? 然后从那里我一直在网上搜索想法

【问题讨论】:

  • 向我们展示您现有的代码。
  • @echo off cls setlocal EnableDelayedExpansion set "cmd=findstr /R /N "^^" file.txt | find /C ":"" for /f %%a in ('!cmd! ') do set number=%%a echo %number% >>list.txt 我从这里找到它不是我的代码stackoverflow.com/questions/5664761/… 然后从那里我一直在网上搜索文件夹中每个csv文件的想法.主要原因是我正在使用超过一百万行的文件,并且想在尝试使用 excel 之前知道有多少行。
  • @DRLINUX,用您的代码编辑您的问题并删除您的评论。
  • 如果您能给出所需输出的简短示例也会很有帮助。
  • OK 代码添加到主要问题。所需的输出也在那里我希望 txt 文件具有 csv 的名称,后跟 csv 中的行数

标签: csv batch-file cmd


【解决方案1】:

在最简单的形式中,您可以使用 find 命令来计算每个文件中的行数。

find /C /V "" file*.csv>count.log

这将输出类似这样的内容。

---------- FILE1.CSV: 19

---------- FILE2.CSV: 28

---------- FILE3.CSV: 3

如果你想去掉空行和前导连字符,你可以通过FOR /F 命令运行它。

@echo off
FOR /F "tokens=* delims=- " %%G IN ('find /C /V "" file*.csv') DO ECHO %%G>>count.log

这会给你这样的输出。

FILE1.CSV: 19
FILE2.CSV: 28
FILE3.CSV: 3

编辑:

这是我的修改版本,因为您显然不喜欢输出中的冒号。

set total=0
(
FOR /F "tokens=1* delims=:" %%G IN ('find /C /V "" *.csv') DO (
    FOR /F "Tokens=1* delims= " %%I IN ("%%~G") DO ECHO %%J %%H&set /a total+=%%H
)
CALL ECHO Total %%total%%
)>List.txt

这里有一些使用 Magoo 的管道逻辑的定时结果,Magoo 使用重定向逻辑和直接从查找结果中挖掘的结果。这是使用包含 8,895,540 行的 437MB 文件进行测试的。

Magoo Pipe:        0 Days 0 Hours 0 Minutes And 15.19 Seconds
Magoo Redirection: 0 Days 0 Hours 0 Minutes And 5.471 Seconds
Squashman File:    0 Days 0 Hours 0 Minutes And 5.429 Seconds

【讨论】:

    【解决方案2】:
    @echo off
    cls
    setlocal EnableDelayedExpansion
    set /a total=0
    (
     for %%f in (*.csv) do (
      for /f %%a in ('type "%%f"^|find /C /v  "" ') do set /a total+=%%a&echo %%f %%a
     )
     echo total !total!
    )>>list.txt
    
    GOTO :EOF
    

    将每个.csv文件名依次分配给%%f

    type 将该文件放入find 并计算行数。将总数增加找到的计数并显示文件名和单个行数(%%a

    完成后,显示总数。

    将所有输出重定向到list.txt

    【讨论】:

    • 添加总数的好主意。我被告知的一件事是重定向比将文件传送到FIND 更快。 find /C /v "" ^<"%%f"我刚从一个客户那里得到了几百万个记录文件。我会测试这个理论。
    • 这是完美的。我刚刚尝试过,并且在我的文件上工作得很好。我选择这个作为答案是因为它与我已经使用的代码很接近,并且它给出了所需的结果。
    • 我在一个有 8,895,540 行的 437MB 文件上测试了您的代码。管道到 find 命令需要 14.6 秒。使用重定向只需要 5.4 秒。 find /C /v "" <%%f
    【解决方案3】:

    对于包含大量行的文件,这将快很多倍。

    使用cscript //nologo "C:\folder\script.vbs" c <inputfile >outputfilec 仅计算在内。 l 计算并显示行数。它几乎不使用内存。它设置环境变量Filter_LineCount

        If LCase(Arg(0)) = "l" then
            Do Until Inp.AtEndOfStream
                Line=Inp.readline
                Count = Count +1
                outp.writeline Line
            Loop
        ElseIf LCase(Arg(0)) = "c" then
            Do Until Inp.AtEndOfStream
                Line=Inp.readline
                Count = Count +1
            Loop
            outp.writeline Count
        End If
    
        'Create a batchfile that filter.bat will run as last step to set the environmental variable %Filter_LineCount%.
        On Error Resume Next
        Set Fso = CreateObject("Scripting.FileSystemObject")
        Set File = Fso.CreateTextFile("%temp%\FilterExit.bat", True)
        If err.number <> 0 then
            Outp.WriteLine "Error: " & err.number & " " & err.description & " from " & err.source
            err.clear
            wscript.exit
        End If
        File.WriteLine "set Filter_LineCount=" & Count
        File.close
    

    在调用它的批处理文件中将这些行放在最后

    If exist "%Temp%\FilterExit.bat" call "%Temp%\FilterExit.bat"
    If exist "%temp%\FilterExit.bat" del "%Temp%\FilterExit.bat"
    

    行数

    过滤 lc {c|l} 过滤行数 {c|l}

    计算文件中的行数。将计数或行打印到 StdOut,并将环境变量 Filter_LineCount 设置为计数。

    l - prints the lines and sets the environmental variable Filter_LineCount to the count.
    c - prints the count and sets the environmental variable Filter_LineCount to the count.
    

    示例

    filter lc c < "%systemroot%\win.ini"
    

    【讨论】:

      【解决方案4】:

      我喜欢Squashmanapproach,但在极少数情况下文件名以连字符- 开头时会失败。 find 还将所有文件名转换为大写。

      如果你想要原始文件名并且你有以- 开头的文件名,你可以使用这个:

      @echo off
      > "count.log" (
          for %%F in ("file*.csv") do (
              for /F %%E in ('^< "%%~F" find /C /V ""') do (
                  echo(%%~F: %%E
              )
          )
      )
      

      这将input redirection &lt; 用于find command,因此它返回没有任何前缀的纯行数。

      【讨论】:

      • 好吧,我可以删除连字符作为分隔符并使用空格。
      【解决方案5】:

      PowerShell 方式是:

      Get-ChildItem -File *.csv |
          ForEach-Object {[string]::Format('{0} {1}', $_.name, (Get-Content $_.FullName).Length)} |
          Out-File -FilePath countls2.txt -Encoding ASCII
      

      使用不应放入 .ps1 文件的别名:

      gci *.csv|%{[string]::Format('{0}: {1}',$_.name,(gc $_.FullName).Length)}|Out-File countls2.txt ASCII
      

      我预测您会想要在计数之前引用文件名或使用分隔符。如果文件名中有空格字符,那将很有用。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-01-24
        • 2017-04-23
        • 1970-01-01
        • 2019-10-31
        • 1970-01-01
        相关资源
        最近更新 更多