我在批量编程方面不是很有经验。我有点捣乱各种代码,但它并不像我想要的那样工作。
这是问题所在。日志文件在目录中创建。有些是多个条目,有些是单个条目。它们都遵循特定的模式。 F.ex。
START STRING 1234
NAME1 ADRESS1 ETC
NAME2 ADRESS2 ETC
NAME3 ADRESS3 ETC
有时在单个文件中有多个名称条目,有时它只是一个条目。所有文件都有起始字符串。我需要做的是解析这些日志文件并在另一个目录中重新创建它们,文件中每个名称一个文件,每个文件都有一个命名文件的格式。使用上面的例子,它将创建3个文件,每个文件看起来像这样:
START STRING
NAME ADRESS ETC
这是代码sofar。它有点工作..除非目录中有多个日志文件,我最终只有几个条目,其中只有两个START STRING,我需要避免。换句话说,我需要单独浏览每个日志文件,而不是像我想象的那样,将所有日志文件视为一个单独的大文本文件。
@Echo off
@setlocal enableextensions enabledelayedexpansion
:::First find out how many lines a file has.
Set _File=*.log
Set /a _Lines=0
For /f %%j in ('Type %_File%^|Find "" /v /c') Do Set /a _Lines=%%j
set /a "linecount= _Lines"
:::Grab the first line always and then create a new file depending on how many lines the file contained
:LOOP
if %linecount% GEQ 2 (
set /a "linecount = linecount - 1"
set lines=1 %linecount%
set curr=1
for /f "delims=" %%a in ('type *.log') do (
for %%b in (!lines!) do (
if !curr!==%%b echo %%a >> c:\temp\logs\%linecount%.log
)
set /a "curr = curr + 1"
)
)
if %linecount% GEQ 2 (GOTO LOOP)
endlocal
我很确定有更聪明的方法可以做到这一点,但这是我已经得到的。想知道我是否可以简单地匹配起始字符串并以某种方式将其删除,而不删除第一行,或者最好避免将双重启动字符串全部放在一起。
答案 0 :(得分:1)
您的问题描述不明确,但从您的代码判断,我假设您只想在新文件夹中重新创建每个日志文件,只保留每个原始文件的前两行。
如果是这样,那么这就是你所需要的:
@echo off
setlocal
set "sourceMask=.\*.log"
set "targetPath=test"
set "keepCount=2"
for %%F in ("%sourceMask%") do (
<"%%~F" (
for /l %%N in (1 1 %keepCount% ) do (
set "ln="
set /p "ln="
echo(!ln!
)
) >"%targetPath%\%%~nxF"
)
限制:
<CR><LF>
结尾(Windows样式),而不是<LF>
(unix样式)以上解决方案无法满足基于评论的OP需求
编辑:尝试2基于OP的提交中的精炼要求(未经测试)
空行将被忽略 - 可能是一件好事。
该代码旨在成为rubust。它应该处理字符串中的任何字符,包括以;
(或任何其他字符)开头的行和包含!
的行。这就是奇数FOR / F选项字符串和延迟扩展切换的原因。
行长度限制为大约8191个字节。
@echo off
setlocal disableDelayedExpansion
set "sourceMask=.\*.log"
set "targetPath=test"
set "targetName=0"
for %%F in ("%sourceMask%") do (
set "startString="
for /f usebackq^ delims^=^ eol^= %%A in ("%%~F") do (
if not defined startString (set "startString=%%A") else (
set "nameString=%%A"
set /a targetName+=1
setlocal enableDelayedExpansion
(
echo(!startString!
echo(!nameString!
) >"!targetPath!\!targetName!.log"
endlocal
)
)
)
答案 1 :(得分:0)
@ECHO OFF
SETLOCAL ENABLEDELAYEDEXPANSION
:: directories in question
SET destdir=c:\destdir
SET sourcedir=c:\sourcedir
SET /a filecount=0
:: process each .log file in source
FOR %%f IN (%sourcedir%\*.log) DO (
SET "startline="
FOR /f "usebackqdelims=" %%i IN ("%%f") DO (
IF DEFINED startline (
CALL :nextfname
>>!filename! ECHO(%%i
) ELSE (
SET "startline=%%i"
)
)
)
GOTO :eof
::
:: Write the header line to the next NEW destination file
::
:nextfname
SET "filename=%destdir%\%filecount%.log"
SET /a filecount+=1
IF EXIST %filename% GOTO nextfname
>>%filename% ECHO(%startline%
GOTO :eof
这应该做你想要的 - IIUC,来自源中的每个.log
文件,在目标中创建一个包含2行的文件 - 来自相应源日志文件的起始行之后的名称行。 (好吧,如果这不是你想要的,那就是这个例程会做的......)
%%f
。 startline
startline
filename
设置为目标中的新文件名并将起始行写入其中%%i
中的名称行输出到生成的文件名。请注意,ENABLEDELAYEDEXPANSION
允许!filename!
引用filename
的内容,因为它在FOR...%%i...
例程:nextfilename
在其自己的上下文中,因此%var%以其更熟悉的含义使用。例程只是从filecount
建立一个名称并递增filecount
,检查文件是否已经存在,并重复直到找到一个全新的文件名。然后将标题行写入该文件名。