[前の記事]« 文字列を置換し、あとで置換前の文字列に直すバッチ処理
[次の記事]引数の有無の判断方法 »

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

▲カテゴリー「FOR /F」索引へ
▲カテゴリー「文字列の操作」索引へ

[NT4]ファイル中の文字列を置換するバッチ処理

391) ファイルの文字列置換について ウィリッシュこーじ 2003/07/10(木) 11:30


はじめまして。

過去ログを確認したのですが、よくわかりませんでしたので
投稿させて頂きます。

現在、WinNT4.0(SP6a)にて運用しているサーバがあるのですが、
バッチファイルにて、あるファイルの中の文字列を置換するような
ことは可能でしょうか?(そのようなコマンドがあるでしょうか?)

フリーソフトとかで置換することは会社からNGと言われており、
バッチファイルにて実行せよとのことで、少々困っております。

どなたかご存知でしたら、教えて頂けないでしょうか?
よろしくお願い致します。



392) Re:補足します ウィリッシュこーじ 2003/07/10(木) 15:51


どういうことがやりたいのかを補足説明します。

まず、c:\aaa\bbb.txtというファイルがあります。

この"bbb.txt"ファイルの内容は、

File = e:\abc\log1.log
File = e:\def\log2.log
File = e:\ghi\log3.log

だとします。

そこで、1行目の"abc"という文字列を"xyz"に置換できたら
と思っております。

バッチファイル内でこれを実現出来たらと考えております。
よろしくお願い致します。

395) Re2:補足します じゃく 2003/07/10(木) 17:43


こんにちは。

>まず、c:\aaa\bbb.txtというファイルがあります。

>この"bbb.txt"ファイルの内容は、

>File = e:\abc\log1.log
>File = e:\def\log2.log
>File = e:\ghi\log3.log

>だとします。

>そこで、1行目の"abc"という文字列を"xyz"に置換できたら
>と思っております。

もう少し説明を詳しくお願いします。
私がこの説明を読んでもイメージがわかないのです。
次のような疑問が出てくるので。
(1)1行目だけでいいのか?2行目以降はそのままでいいの?
(2)置き換えたい abc とか xyz が可変なのか、固定なのか?
(3)bbb.txtに該当するファイルは1つだけなのか?
   置き換え後bbb.txtを上書きしていいのか?
(4)bbb.txt の中身の構成は常に上記例通りか?

つまり、bbb.txt の中身がずっと同じなのか、サーバ上で
定期的に変化するのかが上記例ではわからないです。
変化するならどのように変わるのかが知りたいです。

もし変化しないなら、次のようなバッチでも上記要求を
満たしてしまいますが、これでは求めているものと違うでしょ?
-------------sample.bat------------
echo File = e:\xyz\log1.log>bbb.txt
echo File = e:\def\log2.log>>bbb.txt
echo File = e:\ghi\log3.log>>bbb.txt


398) Re3:補足します ウィリッシュこーじ 2003/07/11(金) 09:51


じゃくさん、こんにちは。
説明が足らなくごめんなさい。下記に回答致します。

>(1)1行目だけでいいのか?2行目以降はそのままでいいの?
2行目以降にも置換したい文字列(例の場合"abc")があったら
置換したいです。

>(2)置き換えたい abc とか xyz が可変なのか、固定なのか?
置き換えたい文字列は固定です。

>(3)bbb.txtに該当するファイルは1つだけなのか?
>   置き換え後bbb.txtを上書きしていいのか?
該当するファイルは複数あります。出来ることなら1回のバッチで
複数のファイルを処理したいと思います。
置換後はファイルを上書き保存したいです。

>(4)bbb.txt の中身の構成は常に上記例通りか?
中身の構成については、例として挙げただけで、実際には
まったく内容が異なります。

>つまり、bbb.txt の中身がずっと同じなのか、サーバ上で
>定期的に変化するのかが上記例ではわからないです。
>変化するならどのように変わるのかが知りたいです。
ファイルの内容については可変といっていいのでしょうか?
まず、現在会社で使用しているWinNTサーバが2台あり、
1台をメイン、もう1台をサブと表現したときに、メイン
からサブにあるファイルをコピーし、ファイルの内容には
コンピュータ名や、あるアプリで使用しているIDなんかが
登録されているので、それらをサブで使用できる内容に
合わせる必要があるのです。ほぼ定期でファイルがコピーされて
くるのでその都度、その内容をメインからサブの構成に合わせたい
のですが・・・。

これでわかりますでしょうか?DOSについては本当によく知らない
ので、よろしくお願い致します。


400) Re4:補足します じゃく 2003/07/11(金) 13:04


だいたいわかりました。

別サーバにあるファイルリストなどのテキストファイルに
対してフォルダ名などを一括で変換したいと解釈しました。
(間違っていたら指摘願います)

このような感じですか?
使用方法は、
C:\>sample bbb.txt
のように引数に変換したいファイルを指定します。

そのファイルに含まれる文字列 abc は すべて xyz に置き換わります。


---------------------------sample.bat
@echo off
if "%1"=="" goto end
set fname=%1
copy %fname% org-%fname% >nul
copy nul > %fname%
for /f "tokens=1* delims=" %%a in ( org-%fname% ) do (set line=%%a&& call :sub)

del org-%fname%
exit /b

:sub
:この1行下の acb=xyz に置換前と置換後の文字列を指定する。
set l=%line:abc=xyz%
echo %l%>>%fname%
goto :EOF

:end


401) 補足(注意事項) じゃく 2003/07/11(金) 13:09


補足です。
このバッチですが、変換するテキストに ">" "<" "|"など
バッチのリダイレクションなどに使う記号があると
うまく動きません。
例として示された bbb.txt でうまくいくことは確認していますが、本当に処理したいファイルの例が示されていないため、
これ以上の検証は難しいです。あしからず。

>---------------------------sample.bat
>@echo off
>if "%1"=="" goto end
>set fname=%1
>copy %fname% org-%fname% >nul
>copy nul > %fname%
>for /f "tokens=1* delims=" %%a in ( org-%fname% ) do (set line=%%a&& call :sub)

>del org-%fname%
>exit /b

>:sub
>:この1行下の acb=xyz に置換前と置換後の文字列を指定する。
>set l=%line:abc=xyz%
>echo %l%>>%fname%
>goto :EOF

>:end




402) Re6:あと少しなんですが ウィリッシュこーじ 2003/07/11(金) 15:47


じゃくさん、ありがとうございます。
ほぼ期待通りの動きをしているのですが、2点困ったことがあります。

1.Sample.Batの引数として、ファイル名を入力しますが、
フォルダ名を付加してしまうと、

>copy %fname% org-%fname% >nul

上記のコピー時に、下記エラーとなってしまいました。
”ファイル名、フォルダ名、またはボリュームラベルの構文が
間違っています。”

フォルダ名も含めたファイル名を引数として入力したいのですが、
どのように変更したらよいでしょうか?

2.置換されたファイルの内容を確認したところ、置換処理は
成功していましたが、一番先頭行に

”1 個のファイルをコピーしました。”

が追加されていました。何故でしょう?
これは何とかして取り除きたいのですが、どうしたらよいでしょうか?

ちなみに

>exit /b

とありますが、/bスイッチはWinNTではサポートされていないよう
です。(”コマンドの構文に誤りがあります。”となりました)

お願いばかりして申し訳ないですが、よろしくお願いします。





403) Re7:あと少しなんですが じゃく 2003/07/11(金) 16:15


数カ所修正しました。
org-%fname% は単に、org というファイル名固定にしました。
(どうせ消すので)
先頭の1行目のメッセージはミスです。修正済み。
exitは使わないようにしました。


---------------------------sample.bat
@echo off
if "%1"=="" goto end
set fname=%1
copy %fname% org >nul
type nul >%fname%
for /f "tokens=1* delims=" %%a in ( org ) do (set line=%%a&& call :sub)

del org
goto end

:sub
:この1行下の acb=xyz に置換前と置換後の文字列を指定する。
set l=%line:abc=xyz%
echo %l%>>%fname%
goto :EOF

:end


404) Re8:ありがとうございました ウィリッシュこーじ 2003/07/11(金) 16:49


思い通りの動作となり、非常にうれしいです。

じゃくさん、大変ありがとうございました。



393) Re:ファイルの文字列置換について ふぇむ 2003/07/10(木) 16:21


>フリーソフトとかで置換することは会社からNGと言われており、
>バッチファイルにて実行せよとのことで、少々困っております。

「フリーソフト」の範囲がどこまでか、「バッチファイル」の範囲がどこまでか、悩ましいですが...

sed や awk などを使わずに、純粋にDOSコマンドレベルのみで文字列置換はできないと思うので、もし Windows Scripting Host が入っていれば、それをつかって書くのが一番簡単ではないでしょうか。

つまり、WSHArgumentsを使ってコマンドライン引数を取得し、FileSystemObject を使って、ファイルの存在確認し、ReadAll() で全部読み取って、Replace()関数で一気に置換して、結果をファイル出力ないし WScript.Echo で標準出力に返してリダイレクト、とかを行なう VBScriptのテキストファイルを書いて、cscript //nologo とかで起動するようにし、それをラップする(適切な環境チェックや引数を渡す)バッチファイルを書く。実行環境へは、そのバッチとスクリプトファイルを置 く(いずれもテキストファイルのみ)。

「フリーソフトを使うな」というのは環境上の混乱を懸念してのことだと思うので、もしWSH(たしかNTではオプションパックだったかも?)が入っていなければ使えないですね。その場合は、Cか何かで *.exe を作って使う、のでしょうか?

でも、NTのコマンドラインから利用できる sed(sed.exeとか) や awk(gawk.exeとか) もコンパクトな exeファイルのみで別にレジストリも変えなければDLLもないと思うので、このくらいのことで自分で exe を作るくらいなら、sed や awk の exeファイルとテキストのスクリプトファイルとをあわせて実行環境に置く、でもあんまり違わないような気がしますが...



397) Re2:ファイルの文字列置換について ウィリッシュこーじ 2003/07/11(金) 09:23


ふぇむさん、ご回答ありがとうございます。

>「フリーソフト」の範囲がどこまでか、「バッチファイル」の範囲がどこまでか、悩ましいですが...

そうですね。「フリーソフト」「バッチファイル」の範囲も確かに
曖昧かもしれません。

sed や awk さらにWindows Script Hostについては、まったく
説明頂いた内容がわからず、他のサイトで上記の言葉を調べたには、
調べたんですけど理解出来ませんでした。

ごめんなさい。

やはり簡単に素人が手を出せる範疇ではないんでしょうね。


407) Re3:ファイルの文字列置換について ふぇむ 2003/07/12(土) 00:47


>sed や awk さらにWindows Script Hostについては、まったく
>説明頂いた内容がわからず、他のサイトで上記の言葉を調べたには、
>調べたんですけど理解出来ませんでした。
>やはり簡単に素人が手を出せる範疇ではないんでしょうね。

ん~、そんなことはないと思いますが... 何かプログラミング言語の経験はおありですか?単にそのスクリプトでの経験がないというか慣れていらっしゃらないというだけ、と推察します。sed や awk は、UNIX系のシェルのご経験のある方にとっては違和感のないものだと思います。

一般のスクリプト系言語(たとえばUNIX系のbシェル系・cシェル系とか、ご紹介した sed やawk とか、その他 perl や ruby や、それから Windows Scripting Host は使用言語としては Visual Basic Script がメジャーですが、JScript や最近なら C# とかでも組めるのかな?、などなど)の中では、DOSのバッチコマンド系がよっぽど偏屈というか無理があるものなので(^^;、これで無理して複雑なもの を組もうとするよりは、もっと組みやすい、普通のプログラミング言語により近いニュアンスのスクリプトを(単独ないし組み合わせて)使うほうが、生産性も 高いしメンテナンスも楽だと思いますよ。

もしご存知ないとすれば、いい機会だと思いますので、勉強されてみてはいかがでしょう。特に awk はお勧めしますね。定型的なテキストファイルの処理にはとても向きます。rubyなどもオブジェクト指向スクリプトという意味で有意義でしょうね。

DOSバッチコマンドだけだと何百行書こうと実現しづらいものが、awk でスパっと書けたりします。まあ、DOSコマンドの方がシンプルで楽な場合もあるので、現実解としては、よいところを組み合わせて、となると思います。

どこまで楽に書くのか、またどこまで汎用性・拡張性・保守性を担保するのか、などという部分のこだわり次第かもしれません。ふぇむは、個人的に、(そこま での必要もないはずなのに)つい汎用性・拡張性・機能分割・保守性などなどを意識してしまって、DOSコマンドだけで結構数百~1千行近く、というスクリ プトをいつのまにか書いてしまってたりします。(^^; 最近はおもに個人用ばかりですけどね。
  • ◆391.  ファイルの文字列置換について (ウィリッシュこーじ)   2003/07/10(木) 11:30
    •  392.  Re:補足します (ウィリッシュこーじ)   2003/07/10(木) 15:51
      •  395.  Re2:補足します (じゃく)   2003/07/10(木) 17:43
        •  398.  Re3:補足します (ウィリッシュこーじ)   2003/07/11(金) 09:51
          •  400.  Re4:補足します (じゃく)   2003/07/11(金) 13:04
            •  401.  補足(注意事項) (じゃく)   2003/07/11(金) 13:09
              •  402.  Re6:あと少しなんですが (ウィリッシュこーじ)   2003/07/11(金) 15:47
                •  403.  Re7:あと少しなんですが (じゃく)   2003/07/11(金) 16:15
                  •  404.  Re8:ありがとうございました (ウィリッシュこーじ)   2003/07/11(金) 16:49
    •  393.  Re:ファイルの文字列置換について (ふぇむ)   2003/07/10(木) 16:21
      •  397.  Re2:ファイルの文字列置換について (ウィリッシュこーじ)   2003/07/11(金) 09:23
        •  407.  Re3:ファイルの文字列置換について (ふぇむ)   2003/07/12(土) 00:47
 
 


カテゴリー「FOR /F」索引へ
カテゴリー「文字列の操作」索引へ

 

カテゴリー一覧

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


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

資料書籍

About

2003年07月10日 16:20に投稿されたエントリーのページです。

ひとつ前の投稿は「文字列を置換し、あとで置換前の文字列に直すバッチ処理」です。

次の投稿は「引数の有無の判断方法」です。

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

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