0

ファイル1の各行がファイル2のすべての行と比較され、一致が見つからない場合は、その行を別のファイルに書き込みます。

以下は私が書いたコードですが、期待どおりに動作していません。

@echo on
cd path
for /f %%a in (file1.txt) do (
for /f %%b in (file2.txt) do (
if %%a==%%b
(
echo lines are same
) else (
echo %%a >> file3.txt
)
)
)

コマンドの構文が正しくないというエラーが表示されます。これで私を助けてください。

4

3 に答える 3

5

foxidrive が示す FINDSTR メソッドは、特に file2 が大きい場合に、問題にアプローチする最速の純粋なバッチ方法であることは間違いありません。ただし、ファイル 1 の正規表現メタ文字、ファイル 1 の引用符やバックスラッシュなど、失敗する可能性のあるシナリオがいくつかあります。Windows FINDSTR コマンドの文書化されていない機能と制限は何ですか? すべての潜在的な問題について。もう少し作業を行うと、ソリューションの信頼性が向上します。

  • 検索は明示的にリテラルにする必要があります
  • 検索は完全一致 (行全体) である必要があります
  • 検索行のバックスラッシュは次のようにエスケープする必要があります\\
  • 各検索は一時ファイルに保存し、\G:fileオプションを使用する必要があります

また、各行の形式についても説明しません。FOR /F ステートメントは、 and の既定のオプションにより、各行の最初の単語のみを読み取りdelimsます。あなたは何も設定したくないと思います。で始まる行がスキップされないように、オプションを無効にすることもできます。これには、奇妙に見える構文が必要です。引用符で囲まなければならないファイル名を扱う場合に備えて、オプションを追加しました。<tab><space>delimseol;usebackq

@echo off
setlocal disableDelayedExpansion
set "file1=file1.txt"
set "file2=file2.txt"
set "file3=file3.txt"
set "search=%temp%\search.txt"

>"%file3%" (
  for /f usebackq^ delims^=^ eol^= %%A in ("%file1%") do if "%%A" neq "" (
    set "ln=%%A"
    setlocal enableDelayedExpansion
    (echo(!ln:\=\\!) >"%search%"
    findstr /lxg:"%search%" "%file2%" >nul || (echo(!ln!)
    endlocal
  )
)
del "%search%" 2>nul

file2 が含まれておらず\"、大文字と小文字を区別しない検索を実行する余裕がある場合は、非常に高速な 1 行のソリューションがあります。単純に FINDSTR 検索を逆にして、ファイル 2 に存在しないファイル 1 の行を探します。検索は次のようにする必要があります。複数のリテラル検索文字列を使用した FINDSTR の例で一致が見つからないのはなぜですか? .

findstr /livxg:"file2.txt" "file1.txt" >"file3.txt"

\"エスケープの問題により、file2 に含まれている場合、これは機能しません。file2 を前処理して all をエスケープすることもでき\ますが、純粋なバッチ ソリューションに制限している場合は、最初のソリューションを使用することもできます。

REPL.BAT と呼ばれるハイブリッド JScript/バッチ ユーティリティを使用する場合は、非常にシンプルで効率的なソリューションがあります。REPL.BAT は、stdin の各行で正規表現の検索と置換操作を実行し、結果を stdout に書き込みます。

REPL.BAT が現在のディレクトリ、またはパス内のどこかにあると仮定します。

@echo off
setlocal
set "file1=file1.txt"
set "file2=file2.txt"
set "file3=file3.txt"
set "search=%temp%\search.txt"

type "%file2%"|repl \\ \\ >"%search%"
findstr /livxg:"%search%" "%file1%" >"%file3%"
del "%search%" 2>nul

このソリューションでも、大文字と小文字を区別しない比較を実行する必要があることに注意してください。

于 2013-10-07T13:23:38.730 に答える
3

構文エラーは左括弧の配置が間違っているために発生しますが、それでもコードは期待どおりに機能しません。

file1 の各行を file2 の各行と比較しますが、一致が見つからない場合だけでなく、等しくない比較ごとに出力します。

for /f %%a in (file1.txt) do (
    set "matchFound="
    for /f %%b in (file2.txt) do (
        if %%a==%%b (
            echo lines are same
            set matchFound=1
        )
    )

    if not defined matchFound (
        echo %%a is not found in file2
    )
)
于 2013-10-07T11:26:00.433 に答える
1

これを試してください:

@echo on
cd /d "c:\path"
del file3.txt 2>nul
for /f "delims=" %%a in (file1.txt) do (
   set "flag="
     for /f "delims=" %%b in (file2.txt) do (
       if "%%a"=="%%b" set flag=1
     )
   if not defined flag >>file3.txt echo %%a
)

ファイルが大きく、速度が必要な場合は、配列を file2 の内容に設定すると、著しく速度が向上します。

これは、より単純なコードを使用しても機能する可能性がありますが、file1 の内容によっては異なります。

@echo on
cd /d "c:\path"
del file3.txt 2>nul
for /f "delims=" %%a in (file1.txt) do (
     findstr "^%%a$" file2.txt >nul || >>file3.txt echo %%a
)
于 2013-10-07T11:54:33.413 に答える