[前の記事]« 複数ファイル名の4桁年号を2桁にリネームしたい
[次の記事]「KKCFUNCが組み込まれました」のメッセージを回避したい »

関連オンラインソフト配布サイト:
Vector>ダウンロード(top) |>MS-DOSまたは汎用 | >WindowsVista/XP/2000/NT

▲カテゴリー「FC,COMP…ファイルの比較」索引へ

ファイル比較結果の相違点のみ取得したい

732.
ファイル比較結果の相違点のみ取得したい
2004年08月17日(火) 12時35分
エバリオン
環境はWindows2000です
2つのファイルを比較して相違点のみ取得する
MS?DOSコマンドプログラムを作成したいのですが、下記の問題でつまずいてます。
FCコマンドを使用しようと考えていまして、
単純なバッチを作成したのですが
異なる行の上下も一緒に結果へ出力されてしまい、困っております。
下の例でいうとH:\AAAA\1.txtの3だけが欲しいのに2と5
I:\bbbb\2.txtの2と3が付いている状態です。
FCのコマンド仕様上仕方ないようなのですが
何か解決する方法はありますでしょうか?

e.g.
-- 1.txt --
a
b
c
d
e

-- 2.txt --
a
b
d
e

この二つに対して
fc /n /1 H:\aaaa\1.txt I:\bbbb\2.txt
を走らせると
ファイル H:\AAAA\1.txt と I:\BBBB\2.TXT を比較しています
***** H:\AAAA\1.txt
2: b
3: c
4: d
***** I:\BBBB\2.TXT
2: b
3: d
*****
735.
Re:ファイル比較結果の相違点のみ取得したい
2004年08月17日(火) 14時54分
oo
>環境はWindows2000です
>2つのファイルを比較して相違点のみ取得する
>MS?DOSコマンドプログラムを作成したいのですが、下記の問題でつまずいてます。
>FCコマンドを使用しようと考えていまして、
>単純なバッチを作成したのですが
>異なる行の上下も一緒に結果へ出力されてしまい、困っております。
>下の例でいうとH:\AAAA\1.txtの3だけが欲しいのに2と5
>I:\bbbb\2.txtの2と3が付いている状態です。
>FCのコマンド仕様上仕方ないようなのですが
>何か解決する方法はありますでしょうか?

>e.g.
>-- 1.txt --
>a
>b
>c
>d
>e

>-- 2.txt --
>a
>b
>d
>e

>この二つに対して
>fc /n /1 H:\aaaa\1.txt I:\bbbb\2.txt
>を走らせると
>ファイル H:\AAAA\1.txt と I:\BBBB\2.TXT を比較しています
>***** H:\AAAA\1.txt
>2: b
>3: c
>4: d
>***** I:\BBBB\2.TXT
>2: b
>3: d
>*****

どこまで汎用性を考えるかによりますが、例のように「1.txt のほうが 2.txt に比べて1行だけ多い」という状況だけなら、FC結果の4行目だけを取り出せばいいので、
@echo off
setlocal
for /f "skip=3 delims=" %%A in ('fc /n 1.txt 2.txt') do set DIF=%%A&goto nxt
:nxt
echo 違いは "%DIF%"

任意の場合への対応は困難だと思いますが、ある程度条件がつけば書けるかも知れません。例えば1.txtの方が必ず多くて、ファイル中に****で始まる行や!^等の特殊文字が無いとか。FC の出力を睨んで抽出ロジックを記述できれば可能です。
標準コマンドでという条件が無ければ diff 等のunix系ツールを導入するほうが早道と思います。
736.
Re2:ファイル比較結果の相違点のみ取得したい
2004年08月17日(火) 17時44分
エバリオン
OOさんありがとうございます。
>どこまで汎用性を考えるかによりますが、例のように「1.txt のほうが 2.txt に比べて1行だけ多い」という状況だけなら、FC結果の4行目だけを取り出せばいいので、
>@echo off
>setlocal
>for /f "skip=3 delims=" %%A in ('fc /n 1.txt 2.txt') do set DIF=%%A&goto nxt
>:nxt
>echo 違いは "%DIF%"

>任意の場合への対応は困難だと思いますが、ある程度条件がつけば書けるかも知れません。例えば1.txtの方が必ず多くて、ファイル中に****で始まる行や!^等の特殊文字が無いとか。FC の出力を睨んで抽出ロジックを記述できれば可能です。

今回は任意の場合の対応を考えてます。
条件は、必ず1.txtの方が多く、1.txt、2.txt両方とも31****で始まる36桁の半角数字です。

>標準コマンドでという条件が無ければ diff 等のunix系ツールを導入するほうが早道と思います。
738.
Re3:ファイル比較結果の相違点のみ取得したい
2004年08月18日(水) 01時15分
oo
>OOさんありがとうございます。
>>どこまで汎用性を考えるかによりますが、例のように「1.txt のほうが 2.txt に比べて1行だけ多い」という状況だけなら、FC結果の4行目だけを取り出せばいいので、
。。。。
>今回は任意の場合の対応を考えてます。
>条件は、必ず1.txtの方が多く、1.txt、2.txt両方とも31****で始まる36桁の半角数字です。

>>標準コマンドでという条件が無ければ diff 等のunix系ツールを導入するほうが早道と思います。

そういう条件だと、ファイル1の表示部分を先頭行と最終行を除いて表示すればいいので、こんな感じでしょうか。
何かawkスクリプトを書いている気分。
ファイルの中身が数字だけということなら大丈夫ですが、特殊文字が含まれていると上手く行かないケースもあると思いますがそこまでテストはしてません。

@echo off
setlocal enabledelayedexpansion
set F=0
for /f "skip=1 delims=" %%A in ('fc /n %1 %2') do (
 if /i "%%A"=="***** %2" ( set F=0
 ) else if /i "%%A"=="***** %1" ( set F=1
 ) else if !F!==1 ( set F=2
 ) else if !F!==2 ( set F=3&set SAVE=%%A
 ) else if !F!==3 ( echo.!SAVE!&set SAVE=%%A)
)
REM F=0 → ***** に囲まれたファイル1表示の外側
REM F=1 → ファイル1表示の先頭行なので表示しない
REM F=2 → ファイル1表示の2行目。F=3の処理と合わせるため一時保管しておく
REM F=3 → 同3行目以降。最終行かもしれないのですぐに表示出来ないので一時保管する
REM    ただし、さっき一時保管した行があるはずなのでまずそれを表示する
REM ***** %1 と等しい行 → F=1にする
REM ***** %2 と等しい行 → 最終行が保管されているが表示せずF=0にする
739.
Re4:ファイル比較結果の相違点のみ取得したい
2004年08月18日(水) 16時53分
エバリオン

>そういう条件だと、ファイル1の表示部分を先頭行と最終行を除いて表示すればいいので、こんな感じでしょうか。
>何かawkスクリプトを書いている気分。
>ファイルの中身が数字だけということなら大丈夫ですが、特殊文字が含まれていると上手く行かないケースもあると思いますがそこまでテストはしてません。

>@echo off
>setlocal enabledelayedexpansion
>set F=0
>for /f "skip=1 delims=" %%A in ('fc /n %1 %2') do (
> if /i "%%A"=="***** %2" ( set F=0
> ) else if /i "%%A"=="***** %1" ( set F=1
> ) else if !F!==1 ( set F=2
> ) else if !F!==2 ( set F=3&set SAVE=%%A
> ) else if !F!==3 ( echo.!SAVE!&set SAVE=%%A)
>)
>REM F=0 → ***** に囲まれたファイル1表示の外側
>REM F=1 → ファイル1表示の先頭行なので表示しない
>REM F=2 → ファイル1表示の2行目。F=3の処理と合わせるため一時保管しておく
>REM F=3 → 同3行目以降。最終行かもしれないのですぐに表示出来ないので一時保管する
>REM    ただし、さっき一時保管した行があるはずなのでまずそれを表示する
>REM ***** %1 と等しい行 → F=1にする
>REM ***** %2 と等しい行 → 最終行が保管されているが表示せずF=0にする

ありがとうございました。お恥ずかしいかぎりですがあまりにも初心者なので「!F!」の理解に手間取りました。!=%なんですね
最初に最終目的を書けばよかったようですね。
ファイル1とファイル2の差分データを取りたかったので
上記の場合
1.txtに追加のデータがある場合(下記の場合)1.txtのF、Gは取得できなくなってしまいました。やはりDOSコマンドプログラムのみでは難しいでしょうか?

e.g.
-- 1.txt --
a
b
c
d
e
F
G

-- 2.txt --
a
b
d
e
740.
Re5:ファイル比較結果の相違点のみ取得したい
2004年08月18日(水) 18時39分
oo
fc /n 2.txt 1.txt と逆にすれば出来そうですけど、
(***** 2.txt と ***** 1.txt の間の行数が0なら動作を変える)
考え直すのが面倒なので安易な手段で回避することにします。
要は先頭や末尾への追加が発生しないようにすれば前回のロジックが使えるので。

echo off
setlocal enabledelayedexpansion
set WK0=%TEMP%\0-0.tmp
set WK1=%TEMP%\0-1.tmp
set WK2=%TEMP%\0-2.tmp
echo @@@@@@@@@@@@@@@@@@@@>"%WK0%"
COPY "%WK0%"+%1+"%WK0%" "%WK1%" >NUL
COPY "%WK0%"+%2+"%WK0%" "%WK2%" >NUL

set F=0
for /f "skip=1 delims=" %%A in ('fc /n "%WK1%" "%WK2%"') do (
 if /i "%%A"=="***** %WK2%" ( set F=0
 ) else if /i "%%A"=="***** %WK1%" ( set F=1
 ) else if !F!==1 ( set F=2
 ) else if !F!==2 ( set F=3&set SAVE=%%A
 ) else if !F!==3 ( echo.!SAVE!&set SAVE=%%A)
)
del "%WK0%" "%WK1%" "%WK2%" 2>NUL

こういうのを「生け贄定石」と言います。最初や最後が特別処理になる場合、ダミーデータを追加して処理パターンをそろえる。処理後に追加したダミーデータを削除するのでそれが生け贄を捧げて後で殺すようなイメージ。(上記では処理後にダミーデータだけを削除するのが面倒なのでファイルコピーしました)
でもgoogleでヒットしないですね。最近は別の呼び方をするのかな?

ワークファイルを作らず、fc /n 2.txt 1.txt の結果を解析する版はご自分でトライしてみてください。

なお、! の意味については set /? に実例付きで解説があります。 
743.
Re6:ファイル比較結果の相違点のみ取得したい
2004年08月20日(金) 11時09分
エバリオン
>こういうのを「生け贄定石」と言います。最初や最後が特別処理になる場合、ダミーデータを追加して処理パターンをそろえる。処理後に追加したダミーデータを削除するのでそれが生け贄を捧げて後で殺すようなイメージ。(上記では処理後にダミーデータだけを削除するのが面倒なのでファイルコピーしました)
>でもgoogleでヒットしないですね。最近は別の呼び方をするのかな?

>ワークファイルを作らず、fc /n 2.txt 1.txt の結果を解析する版はご自分でトライしてみてください。

>なお、! の意味については set /? に実例付きで解説があります。

ありがとうございました。
何とか出来そうです。 
「生け贄定石」大変勉強になりました。、! の意味ちょっと履き違えてましたね。まったくお恥ずかしい限りです。
今後ともよろしくお願いします。
 
 


カテゴリー「FC,COMP…ファイルの比較」索引へ

 

カテゴリー一覧

FPCU/FPCDIY QUICK LINK online
この上の各ジャンル名をクリックすると、下のウィンドウが切り替わります▼


=リンク集のインデックスはこちら=

資料書籍

About

2004年08月17日 08:07に投稿されたエントリーのページです。

ひとつ前の投稿は「複数ファイル名の4桁年号を2桁にリネームしたい」です。

次の投稿は「「KKCFUNCが組み込まれました」のメッセージを回避したい」です。

他にも多くのエントリーがあります。メインページアーカイブページも見てください。

This site is powered by Six Apart
Movable Type 3.33-ja
このブログについて | 運営:有限会社メディアポート