1

好的,我已经玩了一段时间了,但无处可去。我需要从一行中提取 KB 编号。

我遇到的问题是一些 KB 数字是 6 个字符,有些是 7 个字符,并且似乎无法找到一种方法来错误检测这两个字符。

这导致的两种类型的错误如下

第一个应该只显示 6 个字符,所以它在末尾添加了额外的“-”。

x64 KB890830-   2012\MS12-000\WinSec-KB890830-006-P58310-Windows-KB890830-x64-V4.9.exe 

而第二个错误显示随机“_”,因为它使用显示的第一个 KB 而不是第二个。

ia64    KB_942288   2012\MS12-000\WinSec-KB_942288-007-P58312-WindowsServer2003-KB942288-v4-ia64.exe

编辑批处理文件到目前为止

@ECHO OFF
SETLOCAL enableDelayedExpansion

IF EXIST Export.csv DEL Export.csv
FOR /F "tokens=*" %%I in ('dir /s /b *.*') DO CALl:Generate "%%I"
pause

:Generate
SETLOCAL
IF "%~x1" NEQ ".exe" (
    If "%~x3" NEQ ".msu" (
        GOTO:EOF
    )
)
CALL:FindArchitecture %1
CALL:FindKB %1
CALL:PathFix %1
ECHO %Architecture%,%KB%,%FilePath%>>Export.csv
CALL:Cleanup
ENDLOCAL
GOTO:EOF


:FindArchitecture
ECHO %1 | FINDSTR "x64"
IF "%ERRORLEVEL%"=="0"  (
    SET Architecture=x64
    SET Count+=1
)
ECHO %1 | FINDSTR "x86"
IF "%ERRORLEVEL%"=="0" (
    SET Architecture=x86
    SET Count+=1
)

ECHO %1 | FINDSTR "ia64"
IF "%ERRORLEVEL%"=="0" (
    SET Architecture=ia64
    SET Count+=1
)

IF "%Count%" GTR "1" (
    SET Architecture=Error
)
SET Count=0
GOTO:EOF

:FindKB
set KBNum="%~1"
set "KBNum=!KBNum:*-KB=!"
ECHO !KBNum!|findstr /I /E /R /c:"-KB[0-9][0-9][0-9][0-9][0-9][0-9][0-9]" >nul 
SET "KB=KB!KBNum:~0,7!"
IF "%KB%" NEQ "" GOTO:EOF
ECHO !KBNum!|findstr /I /E /r /c:"-KB[0-9][0-9][0-9][0-9][0-9][0-9]" >nul
SET "KB=KB!KBNum:~0,6!"
GOTO:EOF

:PathFix
set Path_to_convert=%~1
set Reference_path=%~dp0
set FilePath=!Path_to_convert:*%Reference_path%=!
GOTO:EOF

:Cleanup
SET KBNum=
SET KB=
SET Count=
SET Architecture=
set InstallerPath=
set PathRemoval=
set Path=
GOTO:EOF
4

1 回答 1

5

好的 - 在看到 Ken White 和 OP 的评论后进行了重要的编辑。

我不确定您是否需要这个,但是带有正则表达式的 FINDSTR 可以验证该行是否具有以下模式:“-KB”后跟 7 位数字,然后是“-”。

echo somestring|findstr /r /c:"-KB[0-9][0-9][0-9][0-9][0-9][0-9][0-9]-" >nul

然后使用替换从“KB-”开始删除所有内容。

然后使用 FINDSTR 验证剩余的前 7 个字符是否为数字。如果不是,则循环返回并替换到下一个“-KB”等。

然后你只需要取剩下的前 7 个字符。

@echo off
:parseVal
setlocal enableDelayedExpansion
set val="%~1"
echo !val!|findstr /r /c:"-KB[0-9][0-9][0-9][0-9][0-9][0-9][0-9]-" >nul || (
  echo Invalid format - KB value not found
  exit /b
)
:parseVal2
set "val=!val:*-KB=!"
echo !val!|findstr /brc:"[0-9][0-9][0-9][0-9][0-9][0-9][0-9]-" >nul || goto :parseVal2
set "val=KB!val:~0,7!"
echo val=!val!
exit /b


编辑

我不确定你做了什么来接受 6 位数字,但以下正则表达式将适用于任何长度的数字。

对于第一个正则表达式:findstr /rc:"-KB[0-9]*-"
对于第二个正则表达式:findstr /brc:"[0-9]*-"

然后在不知道长度的情况下,可以使用以下任一方法来提取数字:

for /f "delims=-" %%A in ("!val!") do set "val=KB%%A"

或者

set val=KB%val:-=&REM %"
于 2012-08-02T01:23:37.963 回答