[ << ] [ >> ]           [Top] [Contents] [Index] [ ? ]

2. diffの出力書式

diffには,出力書式に対する相互に排他的なオプションがいくつかあ ります.以下のセクションではそれぞれの書式を記述し,二つのサンプル入力ファ イル間の差をdiffが報告する方法を図示します.

2.1 二つのサンプル入力ファイル  Sample diff input files for examples.
2.2 周りの文(コンテクスト)を使用しない差の表示  Showing differences without surrounding text.
2.3 周りの文を用いた差の表示  Showing differences with the surrounding text.
2.4 差異を並べて表示する  Showing differences in two columns.
2.5 編集スクリプトの作成  Generating scripts for other programs.
2.6 If-then-elseを用いたファイルのマージ  Merging files with if-then-else.


2.1 二つのサンプル入力ファイル

diffの出力と,様々なオプションがどのようにしてそれを変更するか をを説明するために多くの例で使用する二つのサンプルファイルを以下に示しま す.

これはファイル`lao'です.

 
The Way that can be told of is not the eternal Way;
The name that can be named is not the eternal name.
The Nameless is the origin of Heaven and Earth;
The Named is the mother of all things.
Therefore let there always be non-being,
  so we may see their subtlety,
And let there always be being,
  so we may see their outcome.
The two are the same,
But after they are produced,
  they have different names.

これはファイル`tzu'です.

 
The Nameless is the origin of Heaven and Earth;
The named is the mother of all things.

Therefore let there always be non-being,
  so we may see their subtlety,
And let there always be being,
  so we may see their outcome.
The two are the same,
But after they are produced,
  they have different names.
They both may be called deep and profound.
Deeper and more profound,
The door of all subtleties!

この例では,最初のhunkには`lao'の最初の二つの行が含まれ,二番目の hunkには`lao'の四行目と対応する`tzu'の二行目と三行目が含まれ, そして,最後のhunkには`tzu'の最後の三行が含まれます.


2.2 周りの文(コンテクスト)を使用しない差の表示

"通常"のdiff出力の書式は,周りの文を付けずに差異部分のそれぞ れのhunkを表示します.そのような出力は,変更されていない周りの行に邪魔さ れず,行が変更された様子を見るには最も明確なときもあります(しかし,周り の文を0行使用した,周りの行を用いた書式や一体化した書式を使用して,同様 な結果を得ることも可能です).しかし,この書式をパッチの送付に広く使用す ることはもうありません.その目的では,周りの文を使用する書式 (see section 2.3.1 周りの文を使用した書式)と,一体化した書式(see section 2.3.2 一体化した書式)がより 好まれます.通常の書式は,古いバージョンのdiffとPOSIX標準 との互換性のため,デフォルトになっています.この出力書式を明示的に選択す るために`--normal'オプションを使用してください.

2.2.1 通常書式の詳細な説明  A detailed description of normal output format.
2.2.2 通常の書式の例  Sample output in the normal format.


2.2.1 通常書式の詳細な説明

通常の出力書式は,一つ以上の差異部分のhunkを含んでいます.それぞれのhunk はファイルの差の一つの領域を表示します.通常の書式のhunkは以下のようにな ります.

 
change-command
< from-file-line
< from-file-line...
---
> to-file-line
> to-file-line...

三つの形式の変更コマンド(`change-command')があります.それぞれ,最 初のファイルの行番号またはカンマで分けられた行の範囲,変更方法の種類を示 す単一文字,そして,二番目のファイルの行番号またはカンマで分けられた行の 範囲です.すべての行番号は,それぞれのファイルのもともとの行番号です.変 更コマンドの形式は以下のとおりです.

`lar'
最初のファイルのl行の後に,二番目のファイルの範囲rに行が追加 されています.例えば,`8a12,15'は,1のファイルの八行目の後に2のファ イルの12--15行が追加されたことを意味します.または,変更が2から1への場合, ファイル2の12--15行が削除されたことを意味します.

`fct'
最初のファイルのfの範囲の行が,二番目のファイルのtの範囲の行 で置換されています.これは,追加と削除の組み合わせに似ていますが,よりコ ンパクトになっています.例えば,`5,7c8,10'は,ファイル1の5--7行がファ イル2の8--10行に変更されたことを意味します.または,変更が2から1への場合, ファイル2の8--10行がファイル1の5--7行に変更されたことを意味します.

`rdl'
最初のファイルから範囲rの行が削除されています.行lは,二番目 のファイルに削除されているようにみえる場所です.例えば,`5,7d3'はファ イル1の5--7行が削除されていることを意味します.または,変更が2から1への 場合,ファイル2の3行目の後にファイル1の5--7行が追加されたことを意味しま す.


2.2.2 通常の書式の例

コマンド`diff lao tzu'の出力は以下のようになります(完全な二つのファ イルの内容はsee section 2.1 二つのサンプル入力ファイル).二つのファイルで異なっている行の みが表示されていることに注目してください.

 
1,2d0
< The Way that can be told of is not the eternal Way;
< The name that can be named is not the eternal name.
4c2,3
< The Named is the mother of all things.
---
> The named is the mother of all things.
> 
11a11,13
> They both may be called deep and profound.
> Deeper and more profound,
> The door of all subtleties!


2.3 周りの文を用いた差の表示

通常,ファイル間の差を見るときは,正確に何が変更されたのかを理解する手助 けとなる,ファイルの差がある行の周りの部分も見たいと思うでしょう.このよ うなファイルの周りの部分をcontext(周りの文)と呼びます.

GNU diffは異なっている行の周りの文を表示する,二つの出力 書式を提供しています.context format(周りの文を用いた書式)unified format(一体化した書式)です.それで,異なっている行が見つかっ た関数やファイルのセクションを追加表示することが可能です.

diffの出力形式で,他人にファイルの新しいバージョンを配布する場 合,彼らがファイルに独自の変更をしている場合でも差分を適用できるように, 周りの文を表示する出力形式の一つを使用すべきです.この状況でも,異なって いる行の周りの文の行をファイル内で探すことで,patchで差分を適 用することが可能です.これらの行が差分が告げている場所から実際には数行離 れていても,patchは行番号を調整し,差分を正しく適用することが 可能です.不完全な差分を適用するためにpatchを使用する詳細は, See section 10.3 不完全なパッチの適用.

2.3.1 周りの文を使用した書式  An output format that shows surrounding lines.
2.3.2 一体化した書式  A more compact output format that shows context.
2.3.3 差異のある領域が存在するセクションの表示  Showing which sections of the files differences are in.
2.3.4 ファイル名の代替物を表示する  Showing alternate file names in context headers.


2.3.1 周りの文を使用した書式

周りの文を使用した出力書式は,異なっている行の周りの文の数行を表示します. それはソースコードの更新部分を配布するための標準的な書式です.

この出力形式を選択するために,`-C lines', `--context[=lines]',または`-c'オプションを 使用してください.これらのオプションのいくつかが受けとる引数lines は,表示する周りの文の行数です.linesを指定しない場合,それはデフォ ルトで三行になります.適切に処理するため,patchは通常少なくと も二行の周りの文を必要とします.

2.3.1.1 周りの文を使用した書式の詳細な説明  A detailed description of the context output format.
2.3.1.2 周りの文を使用した書式の例  Sample output in context format.
2.3.1.3 より少ない周りの文を用いた,周りの文を使用した書式の例  Another sample with less context.


2.3.1.1 周りの文を使用した書式の詳細な説明

周りの文を使用した出力書式は,二行のヘッダを用いて開始され,それは以下の ようになります.

 
*** from-file from-file-modification-time
--- to-file to-file-modification time

タイムスタンプは通常,日付,有理数の秒を使用した時間,そして Internet RFC 2822 format のタイムゾーンを示すため`2002-02-21 23:30:39.942229878 -0800'のよう になります.しかし,LC_TIMEロケールカテゴリが`C'または `POSIX'の場合,伝統的なタイムスタンプ`Thu Feb 21 23:30:39 2002'が使用されます.

ヘッダの内容を`--label=label'オプションを使用して変更するこ とが可能です.2.3.4 ファイル名の代替物を表示するを参照してください.

次に一つ以上の差異のhunkが続きます.それぞれのhunkはファイルの差異のある 部分の一つの領域を表示します.周りの文を使用した書式では,hunkは以下のよ うになります.

 
***************
*** from-file-line-range ****
  from-file-line
  from-file-line...
--- to-file-line-range ----
  to-file-line
  to-file-line...

差異のある行の周りの行は,二つのスペース文字を用いて開始されます.二つの ファイル間で異なっている行は,以下の識別文字の一つで開始され,スペース文 字が続きます.

`!'
二つのファイル間で変更されている一行以上のまとまった部分の行です.この hunk部分の`!'で印が付いている行のまとまりに対応するものが,もう一方 のファイルに存在します.

`+'
最初のファイルには対応するものが無い,二番目のファイルに"挿入された"行 です.

`-'
二番目のファイルには対応するものが無い,最初のファイルから"削除された" 行です.

hunkの変更がすべて挿入されたものの場合,from-fileの行は省略されま す.変更のすべてが削除の場合,to-fileの行は省略されます.


2.3.1.2 周りの文を使用した書式の例

コマンド`diff -c lao tzu'の出力は以下のようになります(完全な二つの ファイルの内容はsee section 2.1 二つのサンプル入力ファイル).差の無い行が三行になるまで, 差がある行の周りの行が表示されていることに注目してください.それらは周り の文の行です.周りの文が重なっているため,最初の二つのhunkは一緒になって いることにも注目してください.

 
*** lao	2002-02-21 23:30:39.942229878 -0800
--- tzu	2002-02-21 23:30:50.442260588 -0800
***************
*** 1,7 ****
- The Way that can be told of is not the eternal Way;
- The name that can be named is not the eternal name.
  The Nameless is the origin of Heaven and Earth;
! The Named is the mother of all things.
  Therefore let there always be non-being,
    so we may see their subtlety,
  And let there always be being,
--- 1,6 ----
  The Nameless is the origin of Heaven and Earth;
! The named is the mother of all things.
! 
  Therefore let there always be non-being,
    so we may see their subtlety,
  And let there always be being,
***************
*** 9,11 ****
--- 8,13 ----
  The two are the same,
  But after they are produced,
    they have different names.
+ They both may be called deep and profound.
+ Deeper and more profound,
+ The door of all subtleties!


2.3.1.3 より少ない周りの文を用いた,周りの文を使用した書式の例

コマンド`diff -C 1 lao tzu'の出力は以下のようになります(完全な二つ のファイルの内容はsee section 2.1 二つのサンプル入力ファイル).ここでは最大一行が報告され ていることに注目してください.

 
*** lao	2002-02-21 23:30:39.942229878 -0800
--- tzu	2002-02-21 23:30:50.442260588 -0800
***************
*** 1,5 ****
- The Way that can be told of is not the eternal Way;
- The name that can be named is not the eternal name.
  The Nameless is the origin of Heaven and Earth;
! The Named is the mother of all things.
  Therefore let there always be non-being,
--- 1,4 ----
  The Nameless is the origin of Heaven and Earth;
! The named is the mother of all things.
! 
  Therefore let there always be non-being,
***************
*** 11 ****
--- 10,13 ----
    they have different names.
+ They both may be called deep and profound.
+ Deeper and more profound,
+ The door of all subtleties!


2.3.2 一体化した書式

一体化した出力書式は周りの文を使用した書式の変形で,冗長な周りの行を省略 していて,よりコンパクトになっています.この出力書式を選択するため, `-U lines',`--unified[=lines]',また は`-u'オプションを使用してください.引数linesは,表示する周 りの行数です.与えられていないとき,デフォルトは三行です.

現在,GNU diffだけがこの書式を生成することが可能で, GNU patchだけがこの書式の差分を自動的に適用することが可能 です.適切に処理するため,patchは通常,少なくとも周りの三行を 必要とします.

2.3.2.1 一体化した書式の詳細な記述  A detailed description of unified format.
2.3.2.2 一体化した書式の例  Sample output in unified format.


2.3.2.1 一体化した書式の詳細な記述

一体化した出力書式は二行のヘッダで開始され,それは以下のようになります.

 
--- from-file from-file-modification-time
+++ to-file to-file-modification-time

タイムスタンプは,日付,有理数の秒を使用した時間,そして Internet RFC 2822 format のタイムゾーンを示すため`2002-02-21 23:30:39.942229878 -0800'のよう になります.

ヘッダの内容を,`--label=label'オプションを用いて変更するこ とが可能です.2.3.4 ファイル名の代替物を表示するを参照してください.

次に,差異部分のhunkが一つ以上続きます.それぞれのhunkはファイルの差異部 分の一つの領域を表示します.一体化した書式のhunkは以下のようになります.

 
@@ from-file-range to-file-range @@
 line-from-either-file
 line-from-either-file...

両方のファイルでの共通部分は,スペース文字で開始されます.二つのファイル 間で実際に差のある行には,以下の左側の列に出力されている指示文字の一つが あります.

`+'
最初のファイルの,ここに一行追加されました.

`-'
最初のファイルから,ここの一行が削除されました.


2.3.2.2 一体化した書式の例

以下は,コマンド`diff -u lao tzu'の出力です(二つのファイルの内容の 完全なものは,see section 2.1 二つのサンプル入力ファイル).

 
--- lao	2002-02-21 23:30:39.942229878 -0800
+++ tzu	2002-02-21 23:30:50.442260588 -0800
@@ -1,7 +1,6 @@
-The Way that can be told of is not the eternal Way;
-The name that can be named is not the eternal name.
 The Nameless is the origin of Heaven and Earth;
-The Named is the mother of all things.
+The named is the mother of all things.
+
 Therefore let there always be non-being,
   so we may see their subtlety,
 And let there always be being,
@@ -9,3 +8,6 @@
 The two are the same,
 But after they are produced,
   they have different names.
+They both may be called deep and profound.
+Deeper and more profound,
+The door of all subtleties!


2.3.3 差異のある領域が存在するセクションの表示

それぞれの変更がファイルのどの部分かを知りたいときもあるでしょう.ファイ ルがソースコードの場合,これは変更された関数を意味します.ファイルがドキュ メントの場合,変更された章や付録を意味します.GNU diffで は,差異のある行の前にあるセクション見出し行で最も近くにあるものを表示す ることで,これを示すことが可能です."セクション見出し"の行は,正規表現 で決定されます.

2.3.3.1 正規表現にマッチする行を表示する  Showing headings that match regular expressions.
2.3.3.2 Cの関数の見出しを表示する  Showing headings of C functions.


2.3.3.1 正規表現にマッチする行を表示する

Cやそれに似た言語以外のソースコードのファイルで差異が生じたセクションを 表示するために,`-F regexp'や `--show-function-line=regexp'オプションを使用してください. diffは,grep形式の正規表現regexpにマッチした行 が,ファイルのセクションの先頭だと考えます.いくつかの一般的な言語に対す る正規表現を以下で提案します.

`^[[:alpha:]$_]'
C, C++, Prolog
`^('
Lisp
`^@node'
Texinfo

このオプションでは出力書式を自動的に選択しません.それを使用するために, 周りの文を使用した書式(see section 2.3.1 周りの文を使用した書式)や,一体化した書式 (see section 2.3.2 一体化した書式)を選択する必要があります.それ以外の出力書式では 効果はありません.

`-F'と`--show-function-line'オプションで,差異があるそれぞ れのhunkの前にある変更されていない最も近い行で与えられた正規表現にマッチ する行を見つけます.そしてその行を,周りの文を使用した書式のアスタリスク がある行の終りに,または一体化した書式の`@@'行に追加します.マッ チする行がない場合は,そのまま変更されずに,hunk出力に出力されます.その 行が40文字以上の場合,それらは最初の40文字だけ出力されます.そのような行 に対し,一つ以上の正規表現を指定することが可能です.diffは,そ れぞれの行に対しそれぞれの正規表現にマッチすることを,最後に与えられたも のから試します.これは,希望があれば`-p'と`-F'を一緒に使用 することが可能だということを意味します.


2.3.3.2 Cの関数の見出しを表示する

Cとそれに似た言語で差異の生じた関数を表示するために,`-p'や `--show-c-function'オプションを使用することが可能です.このオプショ ンで,デフォルトの周りの文の行数を用いた周りの文を使用した出力書式を自動 的にデフォルトにします(see section 2.3.1 周りの文を使用した書式).コマンドラインのどこかで `-C lines'を用いることで,その行数に優先させること可能です. コマンドラインのどこかで`-U lines'を用いることで,その書式 と行数に優先させることが可能です.

`-p'と`--show-c-function'オプションは,一体化した書式が指 定されている場合,`-F '^[[:alpha:]$_]''と同じで,それ以外では `-c -F '^[[:alpha:]$_]''と同じです(see section 2.3.3.1 正規表現にマッチする行を表示する). GNU diffは利便性を目的としてそれらを提供しています.


2.3.4 ファイル名の代替物を表示する

意味が無かったり情報として価値の無い名前を持つ二つのファイルを比較する場 合,周りの文を利用したり一体化した出力書式のヘッダに,名前の変わりのもの をdiffで表示させたいかもしれません.こうするために `--label=label'オプションを使用してください.最初にこのオプ ションを与えると,ヘッダ内の最初のファイルの名前と日付をその引数で置換し, 二回与えると,ヘッダ内の二番目のファイルの名前と日付をその引数で置換しま す.このオプションが二回以上与えられる場合,diff はエラーを報 告します.`--label'オプションは,`-l'や`--paginate' オプションが使用されている(see section 5.2 diff出力のページ分割)とき,prヘッダ内 のファイル名に影響しません.

`diff -C 2 --label=original --label=modified lao tzu'の出力の最初の 二行は以下のようになります.

 
*** original
--- modified


2.4 差異を並べて表示する

diffでは,二つのファイルの差異のリストを並べて生成することが可 能です.縦段落間の溝を用いてファイルは二列にリストアップされます.縦段落 間の溝は以下のマーカの一つを含んでいます.

white space
共通の対応する行です.すなわち,それぞれの行は同じ,または `--ignore'オプション(see section 1.2 空白とタブのスペースの差を抑制する)の一つで無視されている差 しかありません.

`|'
対応する行に差があり,両方とも完全または両方とも不完全です.

`<'
ファイルに差があり,最初のファイルだけに含まれている行です.

`>'
ファイルに差があり,二番目のファイルだけに含まれている行です.

`('
最初のファイルだけに含まれている行ですが,差異は無視されます.

`)'
二番目のファイルだけに含まれている行ですが,差異は無視されます.

`\'
対応する行に差があり,最初のファイルの行のみが不完全です.

`/'
対応する行に差があり,二番目のファイルの行のみが不完全です.

通常出力行は,それは不完全な行が含まれている場合だけ不完全です. See section 3. 不完全な行. しかし,出力行が二つの差異のある行に表示される とき,一方は不完全でもう一方はそうでないかもしれません.この状況では,出 力行は完全ですが,その縦段落間の溝は,最初の行が不完全な場合は`\' で,二番目の行が不完全な場合は`/'で印が付いています.

並べた書式が最も読み易いときもありますが,それには制限があります.それは 通常よりはるかに幅広の出力を生成し,長過ぎると切り詰められます.また,通 常より出力の整列状態に強く依存するので,可変幅フォント,標準的ではないタ ブストップ,または表示不可能な文字を使用している場合,その出力は特に見栄 えが悪くなります.

並べた差異を対話的にマージするために,sdiffコマンドを使用する ことも可能です.ファイルのマージの詳細は,See section 9. sdiffを用いた対話的なマージ.

2.4.1 並べた書式の制御  Controlling side by side output format.
2.4.2 並べた出力の例  Sample side by side output.


2.4.1 並べた書式の制御

`-y'や`--side-by-side'オプションで並べた書式を選択します. 並んでいる出力行には二つの入力行が含まれるので,出力は通常より幅広になり ます.通常は130列出力され,それは伝統的なプリンタの行に適しているはずで す.出力の幅を`-W columns'や`--width=columns' オプションを用いて設定することが可能です.出力は同じ幅で半分に分けられ, 差異に印を付ける小さな縦段落間の溝で分けられています.入力行が長過ぎて出 力の半分に適さないものは,出力で切り詰められます.

`--left-column'オプションで,二つの共通列の左の列のみ出力します. `--suppress-common-lines'オプションで,完全に共通の行の出力を抑制 します.


2.4.2 並べた出力の例

コマンド`diff -y -W 72 lao tzu'の出力は以下のようになります(二つの ファイルの完全な内容は,see section 2.1 二つのサンプル入力ファイル).

 
The Way that can be told of is n   <
The name that can be named is no   <
The Nameless is the origin of He        The Nameless is the origin of He
The Named is the mother of all t   |    The named is the mother of all t
                                   >
Therefore let there always be no        Therefore let there always be no
  so we may see their subtlety,           so we may see their subtlety,
And let there always be being,          And let there always be being,
  so we may see their outcome.            so we may see their outcome.
The two are the same,                   The two are the same,
But after they are produced,            But after they are produced,
  they have different names.              they have different names.
                                   >    They both may be called deep and
                                   >    Deeper and more profound,
                                   >    The door of all subtleties!


2.5 編集スクリプトの作成

出力モードには,to-fileを生成するためにfrom-fileファイルを編 集する,コマンドスクリプトを生成するものもあります.

2.5.1 edスクリプト  Using diff to produce commands for ed.
2.5.2 前置edスクリプト  Making forward ed scripts.
2.5.3 RCSスクリプト  A special diff output format used by RCS.


2.5.1 edスクリプト

diffで,edテキストエディタに最初のファイルを二番目の ファイルに変更するように指示するコマンドを生成することが可能です.以前は これが,あるファイルをもう一つのファイルに自動的に編集することに適した唯 一の出力モードでした.現在は,patchを用いることになり,それは もう時代遅れです.この出力書式を選択するために,`-e'や `--ed'オプションを使用してください.

通常の書式(see section 2.2 周りの文(コンテクスト)を使用しない差の表示)同様,この出力書式では周りの文を全く表示しませ ん.通常の書式とは異なり,(二番目のファイルと差分がある場合,最初のファ イルを生成するために)逆に差分を適用するのに必要な情報を含んでいません.

ファイル`d'に`diff -e old new'の出力が含まれている場合,コマン ド`(cat d && echo w) | ed - old'で`old'が`new'のコピーに なるように編集します.より一般的には,`d1',`d2',..., `dN'がそれぞれ,`diff -e old new1',`diff -e new1 new2', ...,`diff -e newN-1 newN'の出力になっている場合,`(cat d1 d2 ... dN && echo w) | ed - old'で`old'が`new'のコピーにな るように編集します.

2.5.1.1 ed書式の詳細な記述  A detailed description of ed format.
2.5.1.2 edスクリプトの例  A sample ed script.


2.5.1.1 ed書式の詳細な記述

ed出力書式は,一つ以上の差異部分のhunkから成り立ちます.複数行 を変更するコマンドで,edコマンドの成功によって行番号を解釈する 方法に影響しないように,ファイルの終りに近い変更が最初に来ます. ed書式のhunkは以下のようになります.

 
change-command
to-file-line
to-file-line...
.

edは行中のピリオドを入力の終りを示すものとして使用するので, GNU diffは,行中の単一のピリオドを二つのピリオドとして書 き込み,それに続くedコマンドで二つのピリオドを一つに変更するこ とで,変更された行を保護します.ed書式は不完全な行を表現するこ とが不可能なので,二番目のファイルの終りが変更のある不完全な行の場合, diffはエラーを報告し,改行を追加するように要求します.

三種類の変更コマンドがあります.それぞれ,最初のファイルの行番号やカンマ で分離されている行の範囲と変更させる手法を示す単一文字から成り立ちます. すべての行番号は,ファイルの元々の行番号です.変更コマンドの種類は以下の とおりです.

`la'
最初のファイルのl行目の後に二番目のファイルからのテキストを追加し ます.例えば`8a'は,ファイル1の8行目以降に,それに続く行を追加しま す.

`rc'
最初のファイルの範囲rの行を,それに続く行で置換します.追加と削除 の組み合わせに似ていますが,よりコンパクトです.例えば`5,7c'は,ファ イル1の5--7行をファイル2のテキストで変更することを意味します.

`rd'
最初のファイルから範囲rの行を削除します.例えば,`5,7d'は,ファ イル1の5--7行を削除することを意味します.


2.5.1.2 edスクリプトの例

`diff -e lao tzu'の出力は以下のようになります(二つのファイルの完全 な内容は,see section 2.1 二つのサンプル入力ファイル).

 
11a
They both may be called deep and profound.
Deeper and more profound,
The door of all subtleties!
.
4c
The named is the mother of all things.

.
1,2d


2.5.2 前置edスクリプト

diffedスクリプトのような出力を生成することが可能で すが,hunkは(前のものを後ろにする)前方への順序を用いています.コマンドの 書式を若干変更することも可能です.それは,変更した行の前にコマンド文字前 置すること,範囲をスペースで分離した行番号にすること,そして,単一のピリ オドから成り立つhunk行を明示する試みを行なわないことです.ed書 式のように,前置ed書式は,不完全な行を表現することは不可能です.

前置ed書式は,edでもpatchでもこの書式の差 分を適用することが不可能なので,ほとんど役に立ちません.それは主に,古い バージョンのdiffとの互換性のために存在しています.それを選択す るために,`-f'や`--forward-ed'オプションを使用してください.


2.5.3 RCSスクリプト

RCS出力書式は,異なるファイルのバージョンとシステムを管理するために 使用するフリープログラム,Revision Control Systemで使用するために設計さ れています.この出力書式を選択するために,`-n'や`--rcs'を 使用してください.前に書いたed書式(see section 2.5.2 前置edスクリプト)に似てい ますが,それは前に書いたed書式の単一のピリオドを含む行と不完全 な行の問題を避けているので,ファイルの内容の任意の変更を表現することが可 能です.単一のピリオドを含む行でテキストセクションを終える変わりに,それ ぞれのコマンドで影響する行数を指定します.`a'と`d'を組み合わせ たコマンドが,`c'の変わりに使用されます.また,二番目のファイルが変 更されている不完全な行で終る場合,出力も不完全な行で終ります.

`diff -n lao tzu'の出力は以下のようになります(二つのファイルの完全 な内容は,see section 2.1 二つのサンプル入力ファイル).

 
d1 2
d4 1
a4 2
The named is the mother of all things.

a11 3
They both may be called deep and profound.
Deeper and more profound,
The door of all subtleties!


2.6 If-then-elseを用いたファイルのマージ

二つのCソースコードをマージするためにdiffを使用することが可能 です.この書式のdiffの出力は,両方のファイルのすべての行を含み ます.両方のファイルに共通の行は,一回だけ出力されます.差異のある部分は, Cプリプロセッサの指示語の#ifdef name#ifndef name#else,そして#endifで分離されています.出力を コンパイルするとき,マクロnameを定義したり未定義にしたりすることで, バージョンを選択します.

二つのファイルをマージするために,`-D name'や `--ifdef=name'オプションを用いてdiffを使用してく ださい.引数のnameは,#ifdef#ifndefといった指示語 で使用するCプリプロセッサの識別子です.

例えば,wait (&s)の文をwaitpid (-1, &s, 0)に変更し,新旧の ファイルを`--ifdef=HAVE_WAITPID'オプションを用いてマージした場合, 影響する部分のコードは以下のようになるでしょう.

 
    do {
#ifndef HAVE_WAITPID
        if ((w = wait (&s)) < 0  &&  errno != EINTR)
#else /* HAVE_WAITPID */
        if ((w = waitpid (-1, &s, 0)) < 0  &&  errno != EINTR)
#endif /* HAVE_WAITPID */
            return w;
    } while (w != child);

次のセクションで説明する,行のグループを使用した書式と,行の書式を使用す ることで,C以外の言語に対する書式を指定することが可能です.

2.6.1 行のグループを使用した書式  Formats for general if-then-else line groups.
2.6.2 行の書式  Formats for each line in a line group.
2.6.3 If-then-else書式の詳細な説明  A detailed description of if-then-else format.
2.6.4 If-then-else書式の例  Sample if-then-else format output.


2.6.1 行のグループを使用した書式

行のグループを使用した書式で,プログラミング言語とテキストの書式化言語が 含まれる,if-then-elseの入力が可能な多くのアプリケーションに適した書式を 指定することができます.行のグループを使用した書式で,類似した行の連続し たグループに対して出力書式を指定します.

例えば,以下のコマンドで,TeXファイルの`old'と`new'を比較し, 古い領域の周りに`\begin{em}'-`\end{em}'行を書き,新しい領 域の周りに`\begin{bf}'-`\end{bf}'行を書くことで,出力をマー ジします.

 
diff \
   --old-group-format='\begin{em}
%<\end{em}
' \
   --new-group-format='\begin{bf}
%>\end{bf}
' \
   old new

以下のコマンドは上記の例と等価ですが,デフォルトの行のグループを使用した 書式で綴っているので,若干冗長になっています.

 
diff \
   --old-group-format='\begin{em}
%<\end{em}
' \
   --new-group-format='\begin{bf}
%>\end{bf}
' \
   --unchanged-group-format='%=' \
   --changed-group-format='\begin{em}
%<\end{em}
\begin{bf}
%>\end{bf}
' \
   old new

以下はより高度な例で,"plain English"形式の行番号を含むヘッダを用いて 差分リストを出力します.

 
diff \
   --unchanged-group-format='' \
   --old-group-format='-------- %dn line%(n=1?:s) deleted at %df:
%<' \
   --new-group-format='-------- %dN line%(N=1?:s) added after %de:
%>' \
   --changed-group-format='-------- %dn line%(n=1?:s) changed at %df:
%<-------- to:
%>' \
   old new

行のグループを使用した書式を指定するために,以下でリストアップするオプショ ンの一つを使用してください.行のグループを使用した書式のうち四つまで指定 することが可能で,それぞれの行のグループの種類になります.通常 formatはシェルのメタ文字を含んでいるので,引用符で囲むべきです.

`--old-group-format=format'
これらの行のグループは,最初のファイルの行だけに含まれているhunkです.デ フォルトの古いグループの書式は,指定されている場合は変更されたグループの 書式と同じです.それ以外の場合,行のグループはそのまま出力される書式にな ります.

`--new-group-format=format'
これらの行のグループは,二番目のファイルの行だけに含まれているhunkです. デフォルトの新しいグループの書式は,指定されている場合は変更されたグルー プの書式と同じです.それ以外の場合,行のグループはそのまま出力される書式 になります.

`--changed-group-format=format'
これらの行のグループは,両方のファイルの行を含んでいるhunkです.デフォル トで,変更されたグループの書式は,新旧のグループの書式を連結したものにな ります.

`--unchanged-group-format=format'
これらの行のグループは,両方のファイルに共通な行を含んでいます.デフォル トで,変更されていないグループの書式は,行のグループをそのまま出力する書 式です.

行のグループを使用した書式では,通常の文字はそのまま表示されます.伝統的 な仕様は,`%'で開始し以下の形式の一つが続きます.

`%<'
最初のファイルからの行を意味し,それは最後の改行を含めます.それぞれの行 は,古い行の書式に依存して書式化されます(see section 2.6.2 行の書式).

`%>'
二番目のファイルからの行を意味し,それは最後の改行を含めます.それぞれの 行は,新しい行の書式に依存して書式化されます.

`%='
両方のファイルに共通な行を意味し,それは最後の改行を含めます.それぞれの 行は,変更されていない行の書式に依存して書式化されます.

`%%'
`%'を意味します.

`%c'C''
このCは単一文字で,Cを意味します.Cをバックスラッシュ やアポストロフィーにしてはいけません.例えば,`%c':''はコロンを意味 し,if-then-else書式のthen-part内部ではコロンは通常終端文字ですが,その ままの意味になります.

`%c'\O''
このOは,1桁,2桁,または3桁の八進数で,8ビットコードOの文字 を意味します.例えば,`%c'\0''はヌル文字を意味します.

`Fn'
このFは,printfの変換を指定し,nは以下の文字の一つに なり,Fで書式化されるnの値を意味します.

`e'
古いファイルのグループの直前の行番号です.

`f'
古いファイルのグループの最初の行の行番号です.e + 1と同じです.

`l'
古いファイルのグループの最後の行の行番号です.

`m'
古いファイルのグループ直後の行番号です.l + 1と同じです.

`n'
古いファイルのグループの行番号です.l - f + 1と同じです.

`E, F, L, M, N'
同様に,新しいファイルの行です.

printfの変換指定は,`%d',`%o',`%x',または `%X'が可能で,それぞれ,10進数,8進数,小文字の16進数,または大文字 の16進数の出力を指定します.`%'の後に続くオプションを順番に表します. ゼロ以上のフラグの列.最小フィールド幅の整数.そして,ピリオドに続く桁数 の最小値を指定する追加の整数.フラグは,左寄せに対する`-', LC_NUMERICロケールのカテゴリで指定される,グループごとの桁数に分離 する`'',そして,スペースの変わりにゼロでパディングするための `0'です.例えば,`%5dN'はグループの新しい行の数を,五文字幅の フィールドで,printfの書式"%5d"で出力します.

`(A=B?T:E)'
ABに等しい場合はT,それ以外ではEになります. ABはそれぞれ10進数の定数または上記で解釈される単一文字です. この書式指定は,Aの値がBの値に等しい場合はTと等価にな ります.それ以外ではEと等価になります.

例えば`%(N=0?no:%dN) line%(N=1?:s)'は,N(新しいファイルのグルー プの行数)が0の場合は`no lines'と等価で,Nが1の場合は`1 line'と等価で,それ以外の場合は`%dN lines'と等価になります.


2.6.2 行の書式

行の書式は,if-then-else書式での行のグループの部分として入力行から出力行 に持っていく行数を制御します.

例えば,以下のコマンドは,テキストの左に変更を示す単一の文字を用いてテキ ストを出力します.出力の最初の文字は,削除行に対する`-',追加行に対 する`|',そして変更されていない行に対するスペースです.その書式には, 出力に概況が必要な場所では,改行文字が含まれます.

 
diff \
   --old-line-format='-%l
' \
   --new-line-format='|%l
' \
   --unchanged-line-format=' %l
' \
   old new

行の書式を指定するために,以下のオプションの一つを使用してください.シェ ルのメタ文字を含むことが多いので,formatを引用符で囲むべきです.

`--old-line-format=format'
最初のファイルからの行だけ書式化します.

`--new-line-format=format'
二番目のファイルからの行だけ書式化します.

`--unchanged-line-format=format'
両方のファイルに共通の行を書式化します.

`--line-format=format'
すべての行を書式化します.影響として,上記の三つのオプションすべてを同時 に設定します.

行の書式では,通常の文字はそれ自身を示します.変換指定は`%'で始め, 以下の形式の一つを用います.

`%l'
行の内容を意味し,後置される改行は(存在しても)数えません.この書式は行が 不完全かどうかを無視します.See section 3. 不完全な行.

`%L'
行の内容を意味し,後置される改行を(存在する場合)含みます.行が不完全な場 合,この書式はその不完全さを保持します.

`%%'
`%'を意味します.

`%c'C''
ここでのCは単一文字で,Cを意味します.Cをバックスラッ シュにしたりアポストロフィーにしたりしてはいけません.例えば, `%c':''はコロンを意味します.

`%c'\O''
ここでのOは1桁,2桁,または3桁の8進数で,8進コードOの文字を 意味します.例えば,`%c'\0''はヌル文字を意味します.

`Fn'
ここでのFprintfの変換指定で,Fで書式化された行番号 を意味します.例えば`%.5dn'は,printfの書式"%.5d"を使 用して行番号を出力します.printf変換指定の詳細は,See section 2.6.1 行のグループを使用した書式.

デフォルトの行の書式は,改行文字が続く`%l'です.

入力にタブ文字が含まれていて,それが出力行にとって重要な場合,行の書式の `%l'や`%L'をタブの直後に書くか(例えば, `%l' や `%L'を前置してタブ文字を使用します),`-t'や `--expand-tabs'オプションを使用すべきです.

行と行のグループの書式を組み合わせると,様々な書式を指定することが可能に なります.例えば以下のコマンドで,通常のdiffの書式に似たものを 使用します.diffの出力を詳細に制御するために,このコマンドに手 を加えることも可能です.

 
diff \
   --old-line-format='< %l
' \
   --new-line-format='> %l
' \
   --old-group-format='%df%(f=l?:,%dl)d%dE
%<' \
   --new-group-format='%dea%dF%(F=L?:,%dL)
%>' \
   --changed-group-format='%df%(f=l?:,%dl)c%dF%(F=L?:,%dL)
%<---
%>' \
   --unchanged-group-format='' \
   old new


2.6.3 If-then-else書式の詳細な説明

両方のファイルで共通の行に対し,diffは変更されていない行のグルー プ書式を使用します.マージされた出力書式の差異部分のそれぞれのhunkに対し, hunkが最初のファイルの行だけを含んでいる場合,diffは古い行のグ ループ書式を使用します.hunkが二番目のファイルの行だけを含んでいる場合, diffは新しい行のグループ書式を使用します.それ以外の場合, diffは変更されたグループ書式を使用します.

古いもの,新しいもの,そして変更されている行の書式はそれぞれ,最初のファ イルの行,二番目のファイルの行,そして両方のファイルに共通の行の出力書式 を指定します.

オプション`--ifdef=name'は,以下のシェルの構文を使用した連 続したオプションと等価です.

 
--old-group-format='#ifndef name
%<#endif /* ! name */
' \
--new-group-format='#ifdef name
%>#endif /* name */
' \
--unchanged-group-format='%=' \
--changed-group-format='#ifndef name
%<#else /* name */
%>#endif /* name */
'

適切に入れ子状にするため,diffの出力を注意深く調べるべきです. 例えば,`-D name'や`--ifdef=name'オプションを 使用するとき,差異のある行がCのプリプロセッサの指示語の`#ifdef', `#ifndef',`#else',`#elif',または`#endif'を含んで いるかどうかを調べるべきで,それらはおそらく入れ子状になっているのでマッ チします.そうでない場合,手動で正しくする必要があります.望んだように本 当になっていることを確実にするため,コードの結果を注意深く調べるのは良い 考えです.入力ファイルが生成される方法に依存して,出力が二重になったもの が含まれたり,正しくないコードになったりします.

patch `-D name'オプションは,ファイルとマージされ たファイルを生成する差分で処理を行なう以外,diff `-D name'と同じように動作します.See section 15.1 patchのオプション.


2.6.4 If-then-else書式の例

`diff -DTWO lao tzu'の出力は以下のようになります(二つのファイルの完 全な内容は,see section 2.1 二つのサンプル入力ファイル).

 
#ifndef TWO
The Way that can be told of is not the eternal Way;
The name that can be named is not the eternal name.
#endif /* ! TWO */
The Nameless is the origin of Heaven and Earth;
#ifndef TWO
The Named is the mother of all things.
#else /* TWO */
The named is the mother of all things.

#endif /* TWO */
Therefore let there always be non-being,
  so we may see their subtlety,
And let there always be being,
  so we may see their outcome.
The two are the same,
But after they are produced,
  they have different names.
#ifdef TWO
They both may be called deep and profound.
Deeper and more profound,
The door of all subtleties!
#endif /* TWO */


[ << ] [ >> ]           [Top] [Contents] [Index] [ ? ]

This document was generated by Akihiro Sagawa on January, 21 2003 using texi2html