使用findstr(ms-dos)进行正则表达式

3

我正在尝试使用MS-DOS命令“findstr”来查找字符串并从文件中删除它。

目前,我可以找到一个明确的字符串,但是我真的很难处理正则表达式。 文件类似于以下内容:

PLs - TULIP Report  
Output_Format, PLS - TULIP REPORT  
NUMLINES,    110907
VARIABLE_TYPES,T1,T8,I,T9,T2,N,N,N  
[[data below]]

该文件是从某个系统导出的,非常恼人的是它有一个标题 - 所以在使用SQL Loader将其导入Oracle数据库之前,我想先进行清理。

不止一个文件,所有文件都会有相同类型的标题,但每个文件略微不同。虽然我很乐意使用硬编码值先删除前两行,例如:

findstr /v "PLs - TULIP Report" "c:\myfiles\file1.PRO"  > "c:\myfiles\file1.csv"</code><br>
findstr /v "Output_Format, PLS - TULIP REPORT" "c:\myfiles\file1.csv" > "c:\myfiles\file2.csv"
(请注意,我用了两个步骤来完成这个过程 - 如果您有任何建议可以在一步中完成,请大力提出)

对于我来说,第三行更加复杂,它将始终以这种格式存在:

NUMLINES,    110907

除了每个文件末尾的数字不同,这一整行都相同。所以我该如何使用正则表达式找到这整行呢?我已经尝试过:
findstr /v /b /r "\D+ \s+ \d+"

但是没有任何运气。

顺便提一下,[[data below]]中的数据如下所示

*,"00000161",456823,"017896532","FU",23.95,3.34,20.61

等等...

显然,我不想修改数据区。

我希望以上内容有意义,

谢谢


+无法工作,使用星号。除非我理解错误,这样可以运行(findstr /B“NUMLINES,*[0-9]*”dos.txt)。我也认为您的字符类\D,\s,\d也不受支持。 - Himanshu
谢谢你 - 我想我走了一条错误的复杂路线!- 只是在其中一个文件上测试了一下,它运行得很好。你知道如何做最后一行吗?即 codeVARIABLE_TYPES,T1,T8,I,T9,T2,N,N,N/code ... 而圣杯是要一次性完成所有这些行! :) ... 或者,我也在尝试使用MORE命令,因为总是需要删除文本文件的前4行,所以我认为它是一个不错的选择,但它非常慢,而且由于某种原因它还挂起了。 - leroyb
是的,你可以使用这个命令(findstr /B VARIABLE_TYPES, dos.txt)。请注意,这假定你的数据中不会有 VARIABLE_TYPES。如果你确定前四行需要跳过,那么你可以使用(more +4 dos.txt)。 - Himanshu
你真的在使用MS-DOS吗?还是你在使用Windows(CMD.EXE)批处理文件? - dbenham
2个回答

1

您必须排除单行,findstr 无法匹配多行。只需用空格分隔不同的正则表达式即可。

findstr /r /b /v "NUMLINES PLs Output_Format" *.txt 
                  ^regex1  ^2  ^3

指定/b可以让您仅在行的开头找到匹配项,而/v则排除这些行。

编辑:

当然,使用方法是

 findstr /r /b /v "NUMLINES PLs Output_Format" yourfile > yourtarget

yourtarget中,您将找到yourfile的数据,除了正则表达式排除的行。

编辑2:

根据您的评论,您只需要将VARIABLE_TYPES添加到您的正则表达式中,使其变为

findstr /r /b /v "NUMLINES PLs Output_Format VARIABLE_TYPES" yourfile > yourtarget

这是一种通过单个指令完成整个操作的方法。


非常感谢Gabber的回答,根据您的建议,我已经编写了以下代码: codefindstr /r /b /v "PLs - Tulip Report Output_Format, PLS - TULIP REPORT NUMLINES, [0-9] VARIABLE_TYPES," sourcefile > targetfilecode,并且它运行得非常好。 - leroyb
当然,我不能使用迷你Markdown标签..<code>fds</code> - leroyb
小心!由于NUMLINES,[0-9],您的编辑将排除以数字开头的行。这些将被视为两个不同的正则表达式!!!另外,在注释中使用代码标记,请单击“帮助”,您将看到迷你markdown格式:) 代码由两个**`**包围(我通常打开帮助并复制并粘贴字符到我的评论中)。 - Gabber

0

这里有一个使用正则表达式的一行代码,可以排除所有四行。(我使用了行续行符,以便代码看起来更好。)每行必须完全匹配。我允许每行以任意数量的空格结尾,因为我不确定你的格式。注意 - FINDSTR 正则表达式支持非常有限且非标准化。还有许多其他 FINDSTR 的怪癖和错误。请参阅 Windows FINDSTR 命令的未记录功能和限制是什么? 以获取更多信息。

findstr /vrx /c:"PLs - TULIP Report *"^
             /c:"Output_Format, PLS - TULIP REPORT *"^
             /c:"NUMLINES, *[0-9]* *"^
             /c:"VARIABLE_TYPES,T1,T8,I,T9,T2,N,N,N *"^
        "c:\myfiles\file1.PRO"  >"c:\myfiles\file1.csv"

如果你只需要跳过前4行,那么通常情况下你应该可以使用MORE命令。但是在处理大文件时,有些情况下MORE命令会卡住,但我无法记起具体情况。此外,MORE命令会将制表符转换为一系列空格。

more +4 "c:\myfiles\file1.PRO"  >"c:\myfiles\file1.csv"

另一个选项是使用 FOR /F 循环。FOR /F 跳过空行,但我认为这对您不是问题。
>"c:\myfiles\file1.csv" (
  for "usebackq skip=4 delims=" %%A in ("c:\myfiles\file1.PRO") do echo(%%A
)

如果你的数据中有任何一个以 ; 开头,那么代码会变得有点丑陋。你需要通过将 EOL 选项设置为换行符来禁用它。
set LF=^


::above 2 blank lines are critical - do not remove
>"c:\myfiles\file1.csv" (
  for usebackq^ skip^=4^ eol^=^%LF%%LF%^ delims^= %%A in ("c:\myfiles\file1.PRO") do echo(%%A
)

关于MORE命令,我也尝试过,但使用它比使用findstr命令要慢得多。 - leroyb

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接