批处理脚本删除多行文本中的回车符,除了每五行一行

时间:2011-03-29 04:51:58

标签: batch-file

我有一个包含以下内容的文本文件:

http://website1.com
http://website2.com
http://website3.com
http://website4.com
http://website5.com
http://website6.com
http://website7.com
http://website8.com
http://website9.com
http://website10.com
http://website11.com
http://website12.com
http://website13.com
http://website14.com
http://website15.com

我希望通过删除除第5,10,15等之外的所有回车/换行符将文本分组为五个“网站”。输出应该类似于:

http://website1.comhttp://website2.comhttp://website3.comhttp://website4.comhttp://website5.com
http://website6.comhttp://website7.comhttp://website8.comhttp://website9.comhttp://website10.com
http://website11.comhttp://website12.comhttp://website13.comhttp://website14.comhttp://website15.com

我该怎么做才能实现这个目标?

3 个答案:

答案 0 :(得分:1)

假设您需要批处理文件,这非常简单:

@echo off
rem We need delayed expansion inside the loop
setlocal enableextensions enabledelayedexpansion
rem Initialize the variables we are going to use to avoid using stale environment vars
set LIST=
set COUNT=0
rem Iterate over the lines in the text file
for /f "delims=" %%l in (list.txt) do (
  rem Append the current line to the list
  set LIST=!LIST!%%l
  rem Count how many we got
  set /a COUNT+=1
  rem If we have five items already
  set /a "COUNT%%=5"
  if !COUNT!==0 (
    rem Output them and reset the list
    echo !LIST!
    set LIST=
  )
)
rem Output the remainder if the list does not contain k×5 lines
if defined LIST echo %LIST%

将该批次的输出重定向到另一个文件,并在需要时将其复制到旧文件上(永远不会重定向到您的输入文件: - ))。

直接写入新输出文件(list_new.txt)的变体:

@echo off
setlocal enableextensions enabledelayedexpansion
set LIST=
set COUNT=0
del list_new.txt
for /f "delims=" %%l in (list.txt) do (
  set LIST=!LIST!%%l
  set /a COUNT+=1
  set /a "COUNT%%=5"
  if !COUNT!==0 (
    >>list_new.txt echo !LIST!
    set LIST=
  )
)
if defined LIST >>list_new.txt echo %LIST%

答案 1 :(得分:0)

如果你有选择,这里有一个Ruby一个班轮

C:\work> ruby -ne 'print $.%5==0? $_ :$_.chomp' file
http://website1.comhttp://website2.comhttp://website3.comhttp://website4.comhttp://website5.com
http://website6.comhttp://website7.comhttp://website8.comhttp://website9.comhttp://website10.com
http://website11.comhttp://website12.comhttp://website13.comhttp://website14.comhttp://website15.com

答案 2 :(得分:0)

根据Joey的解决方案,这仅用于安全处理所有特殊字符%&|<>"!^

如果您希望文件数据中包含!,则只需要这样做 在任何其他情况下,Joey的代码更好,更容易阅读。

@echo off
setlocal EnableExtensions DisableDelayedExpansion
rem Initialize the variables we are going to use to avoid using stale environment vars
set LIST=
set COUNT=0
rem Iterate over the lines in the text file
rem We need toggling the delayed expansion inside the loop
rem always disabled if using %%l, enabled for using the variables
for /f "delims=" %%l in (list.txt) do (
  rem Append the current line to the list, %%l is only safe if delayed expansion is disabled
  set "line=%%l"
  setlocal EnableDelayedExpansion
  rem To use the line variable, delayed expansion has to be enabled
  for %%a in ("!LIST!!line!") do (
    endlocal
    set "LIST=%%~a"
  )

  set /a COUNT+=1
  rem Count how many we got
  rem If we have five items already
  setlocal EnableDelayedExpansion
  if !COUNT! GEQ 5 (
    rem Output them and reset the list
    echo(!LIST!
    endlocal
    set "LIST="
    set COUNT=0
  ) ELSE ( 
    endlocal 
  )
)
setlocal EnableDelayedExpansion
rem Output the remainder if the list does not contain k×5 lines
if defined LIST echo(!LIST!

为何如此复杂?

问题是,%% a(FOR-Loop-Variables)在执行延迟扩展之前被扩展。如果%% a的内容包含任何!,那么您会遇到问题,然后您也会丢失^(仅当存在一个或多个!时)。
但是你需要延迟扩展来显示或比较for循环中变量的内容(忘记调用%% var %%)。
使用延迟语法进行扩展!变量!始终是安全的,独立于内容,因为它是解析器的最后阶段。

但不幸的是启用/禁用延迟exp。总是创建一个新的变量上下文,当离开这个上下文时,你会丢失变量的所有变化 因此,我使用内部FOR-Loop从enabledDelayed-Context返回到disabledDelayed-Context,因此LIST-var包含正确的数据。

希望有人理解我试图解释的内容 关于阶段的更多解释是how cmd.exe parse scripts