用于计算出现次数的批处理文件

时间:2013-12-10 08:34:30

标签: windows batch-file

我有一个这样的纯文本文件:

...
... TYPE: alm01, ........
...
...
...
... TYPE: almBB, ........
...
...
... TYPE: out, ......
...
... TYPE: in, ......
... TYPE: almBB, ........
... TYPE: out, ......
... TYPE: out, ......

(省略号是该行的东西)

所以使用批处理文件或cmd命令(必要时使用管道)我想计算并输出每种类型的出现次数,从上面的示例中,我想输出:

alm01 1
almBB 2
out 3
in 1

我该怎么做?

第一次尝试:(不工作)

@echo off
setlocal enableextensions enabledelayedexpansion

rem Configuration
set "file=test.log"

rem Clean environment
for /f "tokens=1 delims==" %%v in ('set _type_ 2^>nul') do set "%%v="

rem Search required lines
for /f "tokens=*" %%l in ('findstr "TYPE:" "%file%"') do (

    rem Now we have the whole line

    set "t=%%l"

    rem Remove the prefix of the line
    set "t=%t:*TYPE: =%"
    set "t=%t:~1%"

    rem Remove the suffix of the line (from comma to end) and 
    rem increment counter of type
    for /f "tokens=1 delims=," %%t in ('echo %t%') do set /a "_type_%%t+=1"
)

rem Enumerate find types and echo type and number of occurrences
rem The inner loop is to allow underscores inside type
for /f "tokens=1,* delims=_" %%a in ('set _type_ 2^>nul') do (
    for /f "tokens=1,2 delims==" %%v in ("%%a") do echo %%v %%w
)

rem Clean and exit
endlocal
exit /b

1 个答案:

答案 0 :(得分:2)

@echo off
    setlocal enableextensions disabledelayedexpansion

    rem Configuration
    set "file=plaintext.txt"

    rem Clean environment
    for /f "tokens=1 delims==" %%v in ('set _type_ 2^>nul') do set "%%v="

    rem Search required lines
    for /f "tokens=*" %%l in ('findstr "TYPE:" "%file%"') do (

        rem Now we have the whole line
        set "t=%%l"

        rem Can't handle it inside the for loop. Go out to do it
        call :handleType
    )

    rem Enumerate find types and echo type and number of occurrences
    rem The inner loop is to allow underscores inside type
    for /f "tokens=1,* delims=_" %%a in ('set _type_ 2^>nul') do (
        for /f "tokens=1,2 delims==" %%v in ("%%b") do echo %%v %%w
    )

    rem Clean and exit
    endlocal
    exit /b

:handleType
    rem Remove the prefix of the line
    set "t=%t:*TYPE: =%"
    rem Remove spaces (not needed as OP stated and giving problems)
    set "t=%t: =%"

    rem Remove the suffix of the line (from comma to end) and 
    rem increment counter of type
    for /f "tokens=1 delims=," %%t in ("%t:"=%") do set /a "_type_%%~t+=1"

    goto :EOF

EDITED

问题是真实文件在行内部包含一些特殊字符(至少!),并且由于启用了延迟扩展而扩展了这些字符,从而生成OP指示的错误。

要处理它,延迟扩展需要关闭,但由于我们正在读取for循环中的文件,要访问变量的变量值,延迟扩展需要打开,所以,请将其关闭并移动类型管理的代码行,用于for循环外的子程序。