【问题标题】:AWK equivalent in windows batch scriptWindows 批处理脚本中的 AWK 等效项
【发布时间】:2015-03-16 12:21:16
【问题描述】:

我有一个文件 test.txt 为

:ROOM1: :CITY: :2000:
:ROOM2: :RURAL: :1500:
:ROOM3: :CITY: :3000:

我需要根据第一个词和第二个词得到最后一个词。我使用 AWK 在 Unix 中实现了它:

cat get_room_rent.ksh
#!/bin/ksh
FILE_NAME=test.ksh
awk -F: '{ if ($2 == room_name && $4 == type) {print $6} }' room_name=$1 type=$2 $ROOM_RENT
echo ${ROOM_RENT}

运行上面的脚本

RM_RNT=`./get_room_rent.ksh ROOM2 RURAL`

输出

1500

我需要在 Windows 批处理文件中做同样的事情...我不会安装 AWK Windows 版本。

我尝试了类似下面的方法,但我没有运气......

FOR /F "tokens=%ROOM2% delims=:" %%G IN (C:test.txt) DO echo Chosen word is: %%G&goto nextline
:nextline

set showme=Y
FOR /F "tokens=%ROOM2% delims=:" %%G IN (c:test.txt) DO if defined showme set showme=&echo Chosen word is: %%G

【问题讨论】:

  • "我不会安装 awk windows 版本" - 为什么不呢?对我来说似乎容易多了。您可以使用 awk 为不需要任何安装的 Windows 下载 ZIP 文件,例如这里:unxutils.sourceforge.net
  • 我做不到。它是一个受限制的服务器,需要管理它默认拥有的东西。

标签: batch-file batch-processing


【解决方案1】:
@echo off
    setlocal enableextensions disabledelayedexpansion

    set "ROOM_RENT=data.txt"

    rem Option 1 - First filter the contents
    for /f "tokens=5 delims=:" %%a in ('
        findstr /r /c:"^:%~1:[^:]*:%~2:" "%ROOM_RENT%"
    ') do echo %%a

    rem Option 2 - Iterate the file checking the fields
    for /f "usebackq tokens=1,3,5 delims=:" %%a in ("%ROOM_RENT%") do (
        if "%%~a"=="%~1" if "%%~b"=="%~2" echo %%~c
    )

使用get_room_rent.cmd ROOM2 RURAL 调用批处理文件,您将检索到所需的信息。

for /f 命令使用指定的字符作为分隔符拆分记录。拆分记录后,tokens 子句指示要检索的标记列表(每个标记的索引)。

在第一个选项中,检索到的唯一标记是第五个,因为过滤行以仅检索匹配的行。在第二种情况下,检索三个涉及的令牌以处理测试。

为什么令牌的数量与 AWK 代码中的不匹配? for /f 中的分隔符处理丢弃了行首的起始分隔符,从这里开始编号差异。最初的:被丢弃,房间名称成为记录中的第一个字段。

【讨论】:

  • +1,但您可能会提到将/i 添加到findstrif 语句可以允许不区分大小写的匹配。
  • @rojo,问题中的awk 代码区分大小写。批处理代码只是复制预期的行为。
【解决方案2】:

好吧,我认为您对 for /f 循环中 tokens 参数的语法有误。该值应该是数字,并确定在填充 %%G 之前要跳过多少列。

虽然这不会像 awk 那样高效,但最简单的解决方案是将findfindstr 传递给findstr——每个参数一次。

for /f "tokens=3" %%I in (
    'findstr /i "%~1" "test.txt" ^| findstr /i "%~2"'
) do set "showme=%%I"

if defined showme echo Chosen word is %showme::=%

我认为这无论如何都会奏效。我没有测试过。将其称为batfile.bat room2 rural。如果您希望搜索区分大小写,请从 findstr 命令中删除 /i 开关。

【讨论】:

    【解决方案3】:

    IMO PowerShell 是一个更好的解决方案。这是一种方法:

    param($s1, $s2)
    get-content "test.txt" | foreach-object {
      $row = ($_ -split ' ') -replace ':',''
      if ( ($s1 -eq $row[0]) -and ($s2 -eq $row[1]) ) {
        $row[2]
      }
    }
    

    【讨论】:

      猜你喜欢
      • 2012-09-28
      • 2021-03-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-09-18
      • 2010-10-06
      • 2016-05-22
      相关资源
      最近更新 更多