以设置的字符开头的行之间search

首先,我从来没有真正使用批处理,但我试图完成一些事情,并开始感到不知所措。 子目录中有一堆* txt文件。 我想要search这些* txt文件,如果它们不包含某个string(ABCDEF)并将结果输出到一个新文件中。

如果一个文件包含ABCDEF:

输出文件path和名称以及以“[”开头的每一行的内容。

如果一个文件包含一次或多次ABCDEF:

search以“[”开头的行之间的search,如果未find,则输出以“[”开始的两行中的第一行,并像那样移动整个文件。

我的文件是这样的:

[ID1]
包含abcdef的文本
[ID2]
包含abcdef的文本
[ID3]
包含abcdef的文本

这里我的示例输出应该是:

文件名
[ID1]
[ID3]


要求的附加说明

我有一堆AD用户组日志在不同的文件夹中。 这些随机时间导出并保存为* .txt。 这些文件仅包含几行到几百行,并且都以相同的方式设置(如上所示)。

我的关于伪代码的想法是,如下:

Loop through all folders and subfolders Go through the files file by file var output var searchString = abcdef var currentfile = Current File Name/Path While nextline != End of File{ If currentline[0] = "[" output = currentline While nextline[0] != "[" If currentline.contains(searchString) If currentfile != 0{ echo currentfile } echo output currentfile = 0 break else continue } 

所以非常多:寻找searchstring,如果你发现:输出最后一行,开始与“[”,然后继续寻找


添加我到目前为止:我设法得到包含名称的文件,并获取第一个GUID,因为它始终是第一行。
可惜/ v没有工作,因为一行不包含searchstring评估为真。

编辑我得到它,因为我现在能够通过用||代替&&来获得所有不包含我的searchstring的文件。 现在,如果我得到它输出的所有行开始[在这些文件中,我已经完成了一半 。 现在,我必须find一种方法来search以“[”开头的行之间的块,如果没有find,则返回值。 也许有人有小费? ^^

这是我的代码到目前为止:

 @echo off & setlocal set "SrcDir=my root directory" set "FileType=txt" set "SearchKey=abcdef" set "LogFile=output.log" set linenum=1 (for /R %%f in ("*.%FileType%") do ( type "%%~f" | findstr /c:"%SearchKey%" > NUL || ( echo %%~f & for /f "delims=" %%a in ('findstr /r /b /c:"\[" "%%~f"') do echo %%a ) )) > "%LogFile%" 

不考虑外部的FOR循环,这可以非常有效地完成,只有FINDSTR :)!

关键是FINDSTR能够跨越换行符进行搜索(它的功能有点像正则表达式一样)。 我在我的答案的底部描述了这个特性什么是Windows FINDSTR命令的未记录的功能和限制? 。

 @echo off setlocal set "SrcDir=my root directory" set "FileType=txt" set "SearchKey=abcdef" set "LogFile=output.log" (set LF=^ %=This creates a linefeed character=% ) ( for /r "%SrcDir%" %%F in ("*.%FileType%") do ( echo %%~fF cmd /v:on /c findstr /rvc:"!LF!.*%SearchKey%" "%%F"|findstr /b "[" echo( ) ) >"%LogFile%" 

我分两步解决问题。 第一个FINDSTR返回不包含搜索关键字的行之前的所有行。 该结果被传送到第二个FINDSTR,该FINDSTR只返回以[开始的行。

管道的每一侧都在禁用延迟扩展的新cmd.exe进程中执行。 但是LF变量必须使用延迟扩展进行扩展。 这就是为什么我明确地执行一个新的cmd.exe会话中的左侧,通过/v:on启用延迟扩展。

另一个选项是我的JREPL.BAT正则表达式文本处理实用程序 。 这是纯粹的脚本(混合批处理/ JScript),从XP以上的任何Windows机器上本机运行 – 不需要第三方exe文件。

我只需要为每个文件调用JREPL。

 @echo off setlocal set "SrcDir=my root directory" set "FileType=txt" set "SearchKey=abcdef" set "LogFile=output.log" set "find=^\[[^\r\n]*$(?!\r?\n[^\r\n]*%SearchKey%)" set "repl=" ( for /r "%SrcDir%" %%F in ("test*.%FileType%") do ( echo %%~fF call jrepl find repl /v /m /match /f "%%F" echo( ) ) >"%LogFile%" 

如果我得到的要求是错误的,并且[id]下面的所有行应该被搜索,直到下一个[id ],那么FINDSTR解决方案不能被修改工作。 但是JREPL搜索很容易被修改,只要改变FIND的定义就可以扩展搜索直到下一个[id]

 set "find=^\[[^\r\n]*$(?!(?:\n(?!\[)|.)*%SearchKey%)" 

可以用“旗”来完成

 @echo off setlocal EnableDelayedExpansion set searchkey=abcdef set flag=1 for /r %%f in (*.txt) do ( echo %%f set "key=" for /f "usebackq delims=" %%a in ("%%f") do ( echo %%a|find "[" >nul && ( if not defined flag if defined key echo !key! set "key=%%a" set "flag=" ) echo %%a|find "%searchkey%" >nul && set flag=1 ) if not defined flag if defined key echo !key! ) 

key记得最后的[something]

对于&&|| 呃 ,看SS64

对于!variable! 语法看延迟扩展