ラベル sedとawk の投稿を表示しています。 すべての投稿を表示
ラベル sedとawk の投稿を表示しています。 すべての投稿を表示

2015年5月22日

書体見本を自動生成する

大阪DTPの勉強会の隔週勉強会で「書体見本を自動生成する」という宿題が出た。
それを今日、発表することになってしまった。そのためのレジュメ代わり。
(22日21:36 いろいろ修正しました)

書体見本の自動生成

処理の方針:


タブ区切りのフォントリストから、タグ付きテキストを作り、それをInDesingに配置する。自分のコンピュータで使えるすべてのフォントをふくむリストの作り方はこの記事の末尾に書いておきましたが、ここではフォントリスト(サンプルのダウンロード )ができているとして、それからタグ付きテキストを作る方法を紹介します。

スタート:フォントのファミリー名とスタイル名がタブで区切られているリストから、
小塚明朝 Pr6N R
游ゴシック体 ミディアム
……
……
ゴール:次のようなInDesignの「タグ付き」テキストを作る。
<UNICODE-MAC>
<vsn:9.3><fset:InDesign-Japanese>
<pstyle:><cf:小塚明朝 Pr6N><ct:R>小塚明朝 Pr6N R
Lorem ipsum dolor sit amet, consectetur adipisicing elit,
あのイーハトーヴォのすきとおった風、夏でも底に冷たさをもつ青いそら、うつくしい森で飾られたモーリオ市、郊外のぎらぎらひかる草の波。
祇辻飴葛蛸鯖鰯噌庖箸
Lorem ipsum dolor sit amet,
1234567890
12234567890
<ct:><cf:>
<pstyle:><cf:游ゴシック体><ct:ミディアム>游ゴシック体 ミディアム
Lorem ipsum dolor sit amet, consectetur adipisicing elit,
あのイーハトーヴォのすきとおった風、夏でも底に冷たさをもつ青いそら、うつくしい森で飾られたモーリオ市、郊外のぎらぎらひかる草の波。
祇辻飴葛蛸鯖鰯噌庖箸
Lorem ipsum dolor sit amet,
1234567890
12234567890
<ct:><cf:>
……
……

処理の実際:


1)最初に1回だけ、ファイル開始タグを書き出す。
<UNICODE-MAC>
<vsn:9.3><fset:InDesign-Japanese>
2)フォントリストの1行ずつについて次の操作を繰り返す。
2-1)ファミリー名を変数$1に、スタイル名を変数$2に読み込む。
2-2)雛形の$1、$2にファミリー名、スタイル名を代入して出力する。

雛形:
<pstyle:><cf:$1><ct:$2>$1 $2
Lorem ipsum dolor sit amet, consectetur adipisicing elit,
あのイーハトーヴォのすきとおった風、夏でも底に冷たさをもつ青いそら、うつくしい森で飾られたモーリオ市、郊外のぎらぎらひかる草の波。
祇辻飴葛蛸鯖鰯噌庖箸
Lorem ipsum dolor sit amet,
1234567890
12234567890
<ct:><cf:>

これをPerlやAWKスクリプトで実現すると次のようになる。

Perlスクリプト (ダウンロード)
use utf8;
binmode STDOUT, ':utf8';
binmode STDERR, ':utf8';
binmode STDIN, ':utf8';
print "<UNICODE-MAC>\n<vsn:9.3><fset:InDesign-Japanese>\n";
#print "<UNICODE-WIN>\n<vsn:9.3><fset:InDesign-Japanese>\n";
while (<>) {
 /([^\t]+)\t(.+)/;
 print "<pstyle:><cf:$1><ct:$2>$1 $2\
Lorem ipsum dolor sit amet, consectetur adipisicing elit, \
あのイーハトーヴォのすきとおった風、夏でも底に冷たさをもつ青いそら、うつくしい森で飾られたモーリオ市、郊外のぎらぎらひかる草の波。\
祇辻飴葛蛸鯖鰯噌庖箸とか\
Lorem ipsum dolor sit amet,\
1234567890とか\
12234567890\
<ct:><cf:>";
}

実行例:$ perl -f addtag.pl < fontlist.txt | iconv -t utf-16le > fontsample.txt

AWKスクリプト (ダウンロード)
BEGIN {
 FS = "\t"
 print "<UNICODE-MAC>\n<vsn:9.3><fset:InDesign-Japanese>"
}
{ print \
"<pstyle:><cf:" $1 "><ct:" $2 ">" $1 " " $2 "\n\
Lorem ipsum dolor sit amet, consectetur adipisicing elit, \n\
あのイーハトーヴォのすきとおった風、夏でも底に冷たさをもつ青いそら、うつくしい森で飾られたモーリオ市、郊外のぎらぎらひかる草の波。\n\
祇辻飴葛蛸鯖鰯噌庖箸\n\
Lorem ipsum dolor sit amet,\n\
1234567890\n\
12234567890\
<ct:><cf:>"
}

実行例:$ awk -f addtag.pl < fontlist.txt | iconv -t utf-16le > fontsample.txt

留意点:


(ア)ファイル開始タグと改行コードの組み合わせ:
<UNICODE-MAC>とした場合は改行コードをLFに、
<UNICODE-WIN>とした場合は改行コードをCRLFに。
(イ)途中の処理はUTF-8で行っているので、配置する前にUTF-16 (LE BOM付) に変換しておく。
上の実行例ではiconvコマンドを使って変換した。
(ウ)配置する際、「グリッドフォーマットの適用」のチェックを外しておく。


もうちょっとPerlらしいスクリプト (ダウンロード)
use utf8;
binmode STDOUT, ':utf8';
binmode STDERR, ':utf8';
binmode STDIN, ':utf8';
print "<UNICODE-MAC>\n<vsn:9.3><fset:InDesign-Japanese>\n";
while (<>) {
 chop;
 ($family, $style) = split(/\t/, $_);
 print "<pstyle:><cf:$family><ct:$style>$family $style\
Lorem ipsum dolor sit amet, consectetur adipisicing elit, \
あのイーハトーヴォのすきとおった風、夏でも底に冷たさをもつ青いそら、うつくしい森で飾られたモーリオ市、郊外のぎらぎらひかる草の波。\
祇辻飴葛蛸鯖鰯噌庖箸\
Lorem ipsum dolor sit amet,\
1234567890\
12234567890\
<ct:><cf:>";
}

資料集:


PerlとAWK

OS Xには両方とも最初から入ってます。
Windowsにはどちらも入っていません。Perlなら下のサイトからインストールできます。
ActivePerl:http://www.activestate.com/activeperl

『ADOBE INDESIGN CS5 タグ付きテキストユーザーガイド』

http://www.adobe.com/go/learn_id_taggedtext_cs5_jp
(実際には次のURLへリダイレクトされる)
http://help.adobe.com/ja_JP/indesign/cs/taggedtext/indesign_cs5_taggedtext.pdf

Adobe製品のjavascript入門編

古籏一浩さんの「OpenSpace」 http://www.openspc2.org

利用できるフォント(書体)の名前をテキストフレームに書き出す
CC2014用:http://www.openspc2.org/book/InDesignCC2014/easy/font/002/index.html
CC用:http://www.openspc2.org/book/InDesignCC/easy/font/002/index.html
CS6用:http://www.openspc2.org/book/InDesignCS6/easy/font/002/index.html
これで書き出したフォントのリスト(タブ区切りテキスト):fontlist.txt


フォントリストの作り方:

自分のコンピュータで使えるフォントのリストを作るには前項、古籏氏作の「利用できるフォント(書体)の名前をテキストフレームに書き出す」javascriptが便利です。javascriptの実行の仕方も古籏氏の「OpenSpace」のInDesign自動化の項に詳しく書いてあります。

実行すると、InDesign文書上にファミリー名とスタイル名の一覧が現れますので、
  1. テキストを全て選択
  2. ファイル→書き出し
  3. 形式「テキストのみ」
  4. エンコーディング「UTF-8」
  5. fontlist.txtなど適当な名前で保存
以上です。



2012年3月28日

ひらがな・カタカナ変換

ひらがなをカタカナに、カタカナをひらがなにそれぞれ変換するperlスクリプト。
これをOS Xのサービスに入れておくと便利かも。

ひらがな→カタカナ
use utf8;
binmode STDOUT, ':utf8'; 
binmode STDERR, ':utf8'; 
binmode STDIN, ':utf8';
while (<>) {
 tr/ぁ-ゖ/ァ-ヶ/;
 s/わ゙/ヷ/;
 s/ゐ゙/ヸ/;
 s/ゑ゙/ヹ/;
 s/を゙/ヺ/;
 tr/ゝゞ/ヽヾ/;
 s/ゟ/ヨリ/;
 print $_;
}

カタカナ→ひらがな
use utf8;
binmode STDOUT, ':utf8'; 
binmode STDERR, ':utf8'; 
binmode STDIN, ':utf8';
while (<>) {
 tr/ァ-ヶ/ぁ-ゖ/;
 s/ヷ/わ゙/;
 s/ヸ/ゐ゙/;
 s/ヹ/ゑ゙/;
 s/ヺ/を゙/;
 tr/ヽヾ/ゝゞ/;
 s/ヿ/こと/;
 print $_;
}



「わ゙ゐ゙ゑ゙を゙」で、trコマンドじゃなくて、sコマンドを使ってるのは、合成用濁点を使っているからです。濁点付きの「わゐゑを」という文字はありませんもん。

なお、小書きの「ヵ」「ヶ」を「ゕ」「ゖ」に変換するのは間違っていると思うけど、ここでは形式的に変換してみました。「ヵ」「ヶ」は「箇」や「个」の略字・異体であって、仮名ではないはず。


 NOTA BENE :  当初「use encoding "utf8";」という指定をしてましたが、これは使うべきではないとのことです(→『404 Blog Not Found』「perl - use encoding; #は黒歴史」)。


2012年3月24日

たくさんのファイルをいっぺんにリネーム

きのうの隔週勉強会で「リネームソフトってWindows用ばっかりや」という声が(一部から)聞こえたけど*、Mac OS Xだと別段必要もないんじゃないかな。Windowsはシェルがしょぼいから、ファイルのリネーム程度のことでもソフトを作らなあかんということですよ。(*実際にはMac用のもたくさんあるようです。私がWindowsのこともMacのことも知らないだけでした^^)

OS Xはunixですから。


勉強会で出て来たのは、「感-5864.ai」という形式の名前を持つファイルを、冒頭の漢字1文字とハイフンまでを外した「5864.ai」という形式の名前にリネームしたい。たくさんあるのを一括処理したいという課題でした。

Terminal(shellはbash)でやれば簡単。
bashの「for name [ in word ] ; do list ; done」構文を使います。

sedでやってみる

まず、考えたのは手に馴染んでいるsedを使うやりかた。
for i in *.ai
> do
> cp $i `basename $i | gsed -e 's/^.-//'`
> done
  1. basenameコマンドでファイル名をテキストとして取得:basename $i
  2. それをパイプを通じてsedに渡し、
  3. 先頭の一文字とそれに続くハイフン(^.-)を削除:s/^.-//
  4. ここまでの実行結果(`basename $i | gsed -e 's/^.-//'`)を新しいファイル名としてcpコマンドに渡す
という手順。

ただし、漢字など多バイト文字はOS X付属のsedではうまく変換できないので、GNU sedが必要です。(bashの環境変数のうちLANGも、LANG=ja_JP.UTF-8とする必要があります)

perlをつかう

そこで、OS X付属のperlを使ってみました。こんな感じです。
for i in *.ai
> do
> cp $i `basename $i | perl -CIO -pe 'use utf8; s/^.-//;'`
> done

【注】当初、「perl -pe 'use utf8; s/^.+-//;'」と書いていて、どうして「+」が必要なんだろうと不思議に思っていたのですが、エンコーディングの指定書式を旧式の「use encoding "utf8"」にすると文字数が思惑どおりになりました。しかし、その後、perlの起動オプション「-C」で出入力のエンコーディングを指定することを教わりました(man perlrun参照)。これでやっと現代的なコードになりました。みなさん、ありがとうございます。


bashだけでできる

そうこうしているうちに、bashだけでできるのに気付きました。こうです。
for i in *.ai
> do
> cp $i ${i/*-/}
> done

変数を展開する際にその一部を書き換える機能をbash自体が持っているんです。
bashのmanpageでは、「Parameter Expansion」項の最後の方に載ってます。
 ${parameter/pattern/string}という構文です。
(今回はpatternの文字列を削除するのでstring文字列は空)

検索パターンの書き方にちょっと癖があるし、機能もsedやperlほどではないのですが、今回のような事例ならこれで充分役立ちます。

2012年3月5日

どこでもunixフィルタ

おとといの記事のつづきです。


OS Xの「サービス」に「シェルスクリプトを実行」を組み込む時、オプションの「ワークフローの実行時にこのアクションを表示」をONにしておけば、その時々でスクリプトを書き換えられるので便利。


環境変数の設定だけしておけば汎用フィルタとなります。
export LANG=ja_JP.UTF-8
これを「汎用篩」という名前で保存しておきます。

では、facebookの投稿欄で使ってみましょう(ブラウザはSafariです)。


無理矢理の例ですが、各教科ごとの平均点を計算させてみます。計算する行を選択して、上で作ったサービス「汎用篩」を呼び出します。


生徒 A  B  C  平均
国語 85 89 84
算数 92 90 88
理科 78 75 80
社会 94 90 92

おとといの例とは違って、「シェルスクリプトを実行」windowが現れます。
ここにスクリプトを書きこみます。

今回はawkスクリプトを書いてみましょう。awkはOS Xネイティブのものでもutf-8テキストをちゃんと扱えます。

awk '{total=$2+$3+$4; avg=total/3; print $0, avg}'


えい!


生徒 A  B  C  平均
国語 85 89 84 86
算数 92 90 88 90
理科 78 75 80 77.6667
社会 94 90 92 92

できました^^

2012年3月3日

InDesign上のテキストをperlやsedで編集

(2016-1-11注記: CS6ぐらいから仕様が変わったのか、InDesignからサービスにテキストを渡せなくなっています。残念 orz)

Macはテキスト処理も強力なのです。なにせunix系ですから。
しかも、Terminalじゃなくても、Webページの入力フォーム内や、もちろんInDesignのフレームグリッド内でもperlやsed、awkを使ったテキスト編集ができてしまうのです。

もう、これだけでもWindowsを捨てて、Macにしなさいと声を大にして言えます。

InDesignだとこんな具合;
洋数字を漢数字に:置換前
置換後
このあと、「六八〇」→「六百八十」と単位語を書き加えたりしなければなりませんが、手間や書き換え間違いはずいぶん減ります。



これは、OS Xの「サービス」という名前のサービスを使っているのです。
「サービス」は選択部分に対して適用されます。(選択部分が何なのかによってサービスメニューの内容が変ります)


「サービス」はOS X付属のAutomator.appで作ります。
Otto君が手にしているのは他ならぬ「パイプ」です。









起動したら「新規作成」ダイアログで「サービス」を選びます。












左側にある「アクション」を右側の編集欄にドラッグして、unixのフィルタをパイプで繫いでいくように、並べていきます。

↑これは「サービス」ではなく「フォルダアクション」の例です
今回作るフィルタで使う「シェルスクリプトを実行」は「アクション」の「ユーティリティ」の中にあります。それを編集欄にドラッグすると…
ここで、「選択されたテキストを出力で置き換える」にチェックを入れるのがミソです(デフォルトではOFFになってます)。

unix流にいうと選択部分を標準入力・標準出力として扱っているのです。
なお、流れるテキストストリームは、文字コード:utf-8、改行:LF (とおもいきや、InDesignのようにCR改行のテキストを渡すものもあるようです)。



シェルには各種のshellが選べます。perl、python、pubyを直接呼び出すこともできます。








それぞれ、あらかじめ、標準入出力用の枠組みが用意されています。perlだとこんな具合。










あとは、やらせたいフィルタスクリプトをここに書いて、適当な名前をつけて保存すれば、メニューバーのアプリケーションメニューやマウス右クリックでのコンテキストメニューでの「サービス」から呼び出せるようになります。

(この段階では特定のスクリプトを書かず、「汎用のフィルタ」とするのも便利です。詳しくは後日の「どこでもunixフィルタ」記事をどうぞ)


なお、自作の「サービス」は、各ユーザの「~/Library/Services/」フォルダに保存されるのですが、Lionからこのフォルダが不可視とされてしまいました。Finderのメニューバーの「移動」をOptionキーを押しながらクリックすると「ライブラリ」に移動できますが、Automatorの「開く」ダイアログには「移動」がないので、Finderのサイドバーにドラッグして登録しておくことをお薦めします。


実例:

▼ 洋数字を漢数字に書き換えるサービスならこんな具合です。shellとしてperlを使ってます。

use encoding 'utf-8';
while (<>) {
 y/0-9/0-9/;
 y/,./,./;
 y/0123456789/〇一二三四五六七八九/;
 y/,./千・/;
 print $_;
}
「use encoding 'utf-8'」と宣言してやれば、仮名漢字スクリプトもOKです。

▼ メールなど改行で体裁を作ってしまったテキストの行を連結させるサービスでは、bashからsedを呼び出しています。

export LANG=ja_JP.UTF-8
tr \\r \\n | /usr/local/bin/sed -f /Users/mt/bin/jointline.sed
「export LANG=ja_JP.UTF-8」で環境変数LANGをutf-8用にするのが肝心。

なお、OS Xネイティブのsedはutf-8をまだうまく扱えないので、GNU Sedを使う必要があります。GNU Sedはソースから、configure→make→make install で簡単にインストールできます。
また、InDesignのようにCR改行テキストを渡すものもあるので、「tr \\r \\n」で改行をLFに揃えます。

この例で呼び出している jointline.sed は2010年6月に書いた「行連結sedスクリプト」です。
:loop
$!N
s/\(.\+\)\n\([^ ]\+\)/\1\2/
t loop
P
D
 は全角空白です。


*改題しました。2012-03-04

2011年11月18日

行連結sedスクリプトを訂正しました

昨年6月に書いた「行連結sedスクリプト」を訂正しました。「ちぇ、動かへんやん」とがっかりされた皆さん、すみません。

スクリプトA: 段落冒頭の字下げを全角空白でしてある原稿用
:loop
$!N
s/\(.\+\)\n\([^ ]\+\)/\1\2/
t loop
P
D

5−6行目が必要でした。スクリプトBも同様です。(実は、ずーっと以前にこのスクリプトを書いた時には、この形だったのですが、しばらくsedを使わないうちに、すっかり頭がなまっていて、昨年6月にはPとDがどう動くかを忘れていたのです。

 は全角空白です。

次の段落の1行目を読み込んだ時、3行目の置換は失敗し、loopを抜けます。
この時、パターンスペースの中身は、
 現在の段落\n 次の段落の1行目
という形になってます。

5行目のコマンドPはパターンスペースの「\n」までの部分を出力します。
つまり、2−3行目でつなげられた部分のうち、
 現在の段落\n
が出力される訳です。

次いで6行目のコマンドDでパターンスペースの「\n」までの部分を削除します。
この時、パターンスペースには、
  次の段落の1行目
が残ります。

コマンドDは処理をスクリプトの先頭に戻します。


sedスクリプトを書く時は、パターンスペースに何が入っているか、よっく考えなければなりませんね。あ〜、難しかった (*_*;

2011年9月27日

ウェブでもvi

わたしのような偏屈もののために、こんなのを開発してくれている人がいます。


では、さっそく試してみましょう^^



まだまだ、一部しか実装されていないようですけど、
ありがたいことです。

2011年9月21日

モールス符号

つまらないsedスクリプトをふたつ…

k2m.sed
#!/usr/local/bin/sed -f
y/いろはにほへとちりぬるをわかよたれそつねならむうゐのおくやまけふこえてあさきゆめみしゑひもせすん/イロハニホヘトチリヌルヲワカヨタレソツネナラムウヰノオクヤマケフコエテアサキユメミシヱヒモセスン/
y/ぁぃぅぇぉっゃゅょ/アイウエオツヤユヨ/
y/ァィゥェォッャュョ/アイウエオツヤユヨ/
y/がぎぐげござじずぜぞだぢづでどばびぶべぼぱぴぷぺぽ/ガギグゲゴザジズゼゾダヂヅデドバビブベボパピプペポ/
s/ガ/カ゛/g
s/ギ/キ゛/g
s/グ/ク゛/g
s/ゲ/ケ゛/g
s/ゴ/コ゛/g
s/ザ/サ゛/g
s/ジ/シ゛/g
s/ズ/ス゛/g
s/ゼ/セ゛/g
s/ゾ/ソ゛/g
s/ダ/タ゛/g
s/ヂ/チ゛/g
s/ヅ/ツ゛/g
s/デ/テ゛/g
s/ド/ト゛/g
s/バ/ハ゛/g
s/ビ/ヒ゛/g
s/ブ/フ゛/g
s/ベ/ヘ゛/g
s/ボ/ホ゛/g
s/パ/ハ゜/g
s/ピ/ヒ゜/g
s/プ/フ゜/g
s/ペ/ヘ゜/g
s/ポ/ホ゜/g
s/イ/・- /g
s/ロ/・-・- /g
s/ハ/-・・・ /g
s/ニ/-・-・ /g
s/ホ/-・・ /g
s/ヘ/・ /g
s/ト/・・-・・ /g
s/チ/・・-・ /g
s/リ/--・ /g
s/ヌ/・・・・ /g
s/ル/-・--・ /g
s/ヲ/・--- /g
s/ワ/-・- /g
s/カ/・-・・ /g
s/ヨ/-- /g
s/タ/-・ /g
s/レ/--- /g
s/ソ/---・ /g
s/ツ/・--・ /g
s/ネ/--・- /g
s/ナ/・-・ /g
s/ラ/・・・ /g
s/ム/- /g
s/ウ/・・- /g
s/ヰ/・-・・- /g
s/ノ/・・-- /g
s/オ/・-・・・ /g
s/ク/・・・- /g
s/ヤ/・-- /g
s/マ/-・・- /g
s/ケ/-・-- /g
s/フ/--・・ /g
s/コ/---- /g
s/エ/-・--- /g
s/テ/・-・-- /g
s/ア/--・-- /g
s/サ/-・-・- /g
s/キ/-・-・・ /g
s/ユ/-・・-- /g
s/メ/-・・・- /g
s/ミ/・・-・- /g
s/シ/--・-・ /g
s/ヱ/・--・・ /g
s/ヒ/--・・- /g
s/モ/-・・-・ /g
s/セ/・---・ /g
s/ス/---・- /g
s/ン/・-・-・ /g
s/゛/・・ /g
s/濁点/・・ /g
s/゜/・・--・ /g
s/半濁点/・・--・ /g
s/ー/・--・- /g
s/、/・-・-・- /g
s/」/・-・-・・ /g
s/(/-・--・- /g
s/)/・-・・-・ /g
s/本文/-・・--- /g
s/訂正/・・・-・ /g
s/終了/・・・-・ /g


m2k.sed
#!/usr/local/bin/sed -f
s/ / /g
s/-・--・- /(/g
s/・-・-・- /、/g
s/・-・-・・ /」/g
s/・-・・-・ /)/g
s/---・- /ス/g
s/--・-- /ア/g
s/--・-・ /シ/g
s/--・・- /ヒ/g
s/-・--- /エ/g
s/-・--・ /ル/g
s/-・-・- /サ/g
s/-・-・・ /キ/g
s/-・・-- /ユ/g
s/-・・-・ /モ/g
s/-・・・- /メ/g
s/・---・ /セ/g
s/・--・- /ー/g
s/・--・・ /ヱ/g
s/・-・-- /テ/g
s/・-・-・ /ン/g
s/・-・・- /ヰ/g
s/・-・・・ /オ/g
s/・・--・ /゜/g
s/・・-・- /ミ/g
s/・・-・・ /ト/g
s/---- /コ/g
s/---・ /ソ/g
s/--・- /ネ/g
s/--・・ /フ/g
s/-・-- /ケ/g
s/-・-・ /ニ/g
s/-・・- /マ/g
s/-・・・ /ハ/g
s/・--- /ヲ/g
s/・--・ /ツ/g
s/・-・- /ロ/g
s/・-・・ /カ/g
s/・・-- /ノ/g
s/・・-・ /チ/g
s/・・・- /ク/g
s/・・・・ /ヌ/g
s/--- /レ/g
s/--・ /リ/g
s/-・- /ワ/g
s/-・・ /ホ/g
s/・-- /ヤ/g
s/・-・ /ナ/g
s/・・- /ウ/g
s/・・・ /ラ/g
s/-- /ヨ/g
s/-・ /タ/g
s/・- /イ/g
s/・・ /゛/g
s/- /ム/g
s/・ /ヘ/g
s/カ゛/ガ/g
s/キ゛/ギ/g
s/ク゛/グ/g
s/ケ゛/ゲ/g
s/コ゛/ゴ/g
s/サ゛/ザ/g
s/シ゛/ジ/g
s/ス゛/ズ/g
s/セ゛/ゼ/g
s/ソ゛/ゾ/g
s/タ゛/ダ/g
s/チ゛/ヂ/g
s/ツ゛/ヅ/g
s/テ゛/デ/g
s/ト゛/ド/g
s/ハ゛/バ/g
s/ヒ゛/ビ/g
s/フ゛/ブ/g
s/ヘ゛/ベ/g
s/ホ゛/ボ/g
s/ハ゜/パ/g
s/ヒ゜/ピ/g
s/フ゜/プ/g
s/ヘ゜/ペ/g
s/ホ゜/ポ/g
y/イロハニホヘトチリヌルヲワカヨタレソツネナラムウヰノオクヤマケフコエテアサキユメミシヱヒモセスン/いろはにほへとちりぬるをわかよたれそつねならむうゐのおくやまけふこえてあさきゆめみしゑひもせすん/
y/ガギグゲゴザジズゼゾダヂヅデドバビブベボパピプペポ/がぎぐげござじずぜぞだぢづでどばびぶべぼぱぴぷぺぽ/

GNU Sedで動きます。

2010年11月1日

串刺しナンバリング:冗談なれど、王立協会は些かも疎かにせず

ワンライナー、私にも書けました!
MacOSXの道具箱(/usr/bin/)にひっそり隠れていたものたち。
ひとつひとつはちっちゃいけれど、力をあわせりゃ、このとおり。

No.1からNo.500までを串刺し8面付にするための連番を生成します。

jot - 1 500 1 | rs -t 0 8 | sed -e 's/ $/b/' | rs 0 1 | sed -e 's/b//' > num.txt


連番の個数がシート数の整数倍でなくて半端がでる場合、最後の何枚かのシートに連番が入らない欄が一つずつできます。そこのところの処理、ちょっと工夫しました。

  • jotで縦1列にならんだ連番を作ります。
  • 1回目のrsで面付された状態と同じように8列に連番が並びます。
  • 500より大きなところは空欄になってます。その行末の直前の空白は、ほんとは列のセパレータのはずですが、それと行末をセットにしてsedでマーク(b)を付けるのです。
  • 2回目のrsで縦1列にならびかえ。
  • 最後にsedでマークを外して、できあがり!


今回登場してくれたのは次のみなさん。sedさんには普段からいろいろお世話になってますけど、jotさんは、やもさんに教えてもらうまで知りませんでした。rsさんは、jotさんのmanpageで見つけました。これからもよろしく ^_^

jot -- print sequential or random data
rs -- reshape a data array
sed -- stream editor

2010年10月30日

串刺しナンバリング:改訂したけど、ウミスズメの黒焼きではありません

連番を任意の数字から始められるようにしてみました。ついでにスクリプト名や変数名を整理しました。(if...else構文も正しくしました:30日21時) ^_^


#  kszs.awk
#
#  使い方:
#  awk  -f  kszs.awk  >  num.txt

BEGIN {

#  連番開始・終了番号と面付数の入力を求める
    printf "開始番号=" > "/dev/stderr"
      getline sn_start < "/dev/stdin"
    printf "終了番号=" > "/dev/stderr"
      getline sn_end   < "/dev/stdin"
    printf "面付数="   > "/dev/stderr"
      getline n_men   < "/dev/stdin"

#  連番の個数を計算する
    n_sn = sn_end - sn_start + 1

#  総シート数(ページ数)を計算する # 以下6行訂正しました
    n = int ( n_sn / n_men )
    if ( n_sn % n_men == 0 ) {
        n_sheet = n
    } else {
        n_sheet = n + 1
    }
##    n_sheet = int ( 0.5 + n_sn / n_men )  # これは間違いでした

#  i は作業中のシート番号
    for ( i = 0; i < n_sheet; i++ ) {

#      j はシート内の面番号
        for ( j = 0; j < n_men; j++ ) {

#          シート番号と連番開始番号との和が
#          そのシート内最初の連番になる
#          また、総シート数の値が連番の増分となる 
            serialnum = i + sn_start + j * n_sheet

#          連番を標準出力に改行付きで書き出す
#          最大数を超えている場合は改行だけを書き出す
            if ( serialnum <= sn_end ) {
                print serialnum
            } else {
                print ""
            }
        }
    }
}


経緯については、前の記事をご参照ください。
    http://lamium.blogspot.com/2010/10/blog-post_30.html

それより、やもさんの新しい記事の方が、串刺しやこの間の経緯がよくわかります。
    Kushizashiはワールドワイドに

串刺しナンバリング:焼き鳥の一品ではござらぬ

串刺し印刷用の連番を生成するawkスクリプトを、私も遅ればせながら作ってみました。

串刺し印刷そのものをよく知らないので、なんか見当違いをしているような気もします。BEGINだけというのもawkスクリプトとしては変則的でしょうね。ご批評くだされ。

★ 総ページ数の計算と、if...else構文を正しくしました(30日21時)


# kusizasinum.awk
#
# 使い方:
#  awk  -f  kusizasinum.awk  >  num.txt


BEGIN {

#       連番最大数と面付数の入力を求める
        printf "最大数="        > "/dev/stderr"
                getline maxnum  < "/dev/stdin"

        printf "面付数="        > "/dev/stderr"
                getline mennum  < "/dev/stdin"

#       総シート数(ページ数)を計算する # 以下6行訂正しました
            n = int ( maxnum / mennum )
            if ( maxnum % mennum == 0 ) {
                    sheetnum = n
            } else {
                    sheetnum = n + 1
            }

#          sheetnum = int ( 0.5 + maxnum / mennum )  # これは間違いでした

#       i は作業中のシート番号
        for ( i = 1; i <= sheetnum; i++ ) {

#               j はシート内の面番号
                for ( j = 0; j < mennum; j++ ) {

#                       シート番号がそのシート内最初の連番になり
#                       総シート数の値が連番の増分となる 
                        serialnum = i + j * sheetnum

#                       連番を標準出力に改行付きで書き出す
#                       最大数を超えている場合は改行だけを書き出す
                        if ( serialnum <= maxnum ) {
                                print serialnum
                        } else {
                                print ""
                        }
                }
        }
}


連番を任意の番号から始められるようにした改訂版はこちら。


なお、この経緯についてはスクリプトの達人のみなさんによる次のページを参照してください。

串刺し会長やまさん:These are the days of my life
  お話してきました。
  串刺し印刷について。

あさうすさん:実験ルーム
  串刺し面付けってなぁに?

やもさん:やもめも
  あえてScriptを使わずに串刺しナンバリングしてみる(小ネタ)
  Kushizashiはワールドワイドに

たけうちとおるさん:たけうちとおるのスクリプトノート
  僕もScriptを使わずに串刺しナンバリング
  僕もScriptを使って串刺しナンバリング

市川せうぞーさん:名もないテクノ手
  あえてScriptを使って串刺しナンバリングしてみる(小ネタ)

chalcedonyさん:
  くしざし試作

2010年9月12日

awkメモ:HTMLのtableに1行おきの背景色をつける

これは自分用のメモです。sed & awk使いには「また、車輪を再発明しとってやがな〜」とそしられそうなものばかりでしょう。

先の記事でつくったような単純なtableの行やセルに体裁をつけます。まずは、1行おきに背景色を指定し、しかも左端の第1列には色をつけない...

BEGIN {
  RS="</tr>"
  FS="<td>"
}

NR % 2 == 1 {
  print $0 RS
}

NR % 2 == 0 {
  print $1\
  "<td>"$2\
  "<td style=\"background-color:#ccffff;\">"$3\
  "<td style=\"background-color:#ccffff;\">"$4\
  "<td style=\"background-color:#ccffff;\">"$5\
  "<td style=\"background-color:#ccffff;\">"$6\
  "<td style=\"background-color:#ccffff;\">"$7\
  "<td style=\"background-color:#ccffff;\">"$8\
  RS  
}

もとのHTMLのソースで、1レコード=複数行にしているので、レコードセパレータ(RS)とフィールドセパレータ(FS)でちょっと無理をさせてます。そのため、$1が「<tr>」に、表の1列めが$2、2列めが$3...と気持ち悪いことになってしまいました。

</td>と改行、インデントは$2〜$8の末尾にそれぞれ入ってます($8にはインデントは入っていませんが)。

1レコード=1行だったもとのタブ区切りテキストを直接、awkに喰わせる方が簡単かもしれません。

レコード番号(NR)の剰余(演算子%)で場合分けをしてますから、「n行おき」の指定も可能です。(↑これが、このスクリプトのミソですね)

なお、上の例では1列目以外は同じ背景色ですが、列毎に書式を指定できますね。

まあ、とりあえずの間に合わせスクリプです (^_^;;

-

sedメモ:タブ区切りテキストからHTMLのtableへ

これは自分用のメモです。sed & awk使いには「また、車輪を再発明しとってやがな〜」とそしられそうなものばかりでしょう。

s#^#<tr>\
  <td>#
s#$#</td>\
</tr>#
s#\t#</td>\
  <td>#g

InDesignで組んだ表を選択してテキストに書き出すと、タブ区切りものが得られますが、それをHTMLでの表に書き直す、その作業の一部。<tr>と<td>タグを書き込む付けるsedスクリプトです。
1レコード=1行の方が後の処理が楽そうですが、出来上がるHTMLソースが読みやすくなるようインデント・改行を加えて、1レコード=複数行の書式にしてます。


こんな風です。

タブ区切りテキスト:
  学校数 給食実施校  未実施校 備考
   完全給食 ミルク給食  
 神戸市 85 2* 83  75校で弁当販売 *は夜間中学
阪神 尼崎市 20 1**  19 **は夜間中学での補食給食
 西宮市 20 20   
 芦屋市 3   3 
これを上のスクリプトで処理すると:
<tr>
  <td></td>
  <td></td>
  <td>学校数</td>
  <td>給食実施校</td>
  <td></td>
  <td>未実施校</td>
  <td>備考</td>
</tr>
<tr>
  <td></td>
  <td></td>
  <td></td>
  <td>完全給食</td>
  <td>ミルク給食</td>
  <td></td>
  <td></td>
</tr>
<tr>
  <td></td>
  <td>神戸市</td>
  <td>85</td>
  <td>2*</td>
  <td>83</td>
  <td></td>
  <td>75校で弁当販売 *は夜間中学</td>
</tr>
<tr>
  <td>阪神</td>
  <td>尼崎市</td>
  <td>20</td>
  <td>1**</td>
  <td></td>
  <td>19</td>
  <td>**は夜間中学での補食給食</td>
</tr>
<tr>
  <td></td>
  <td>西宮市</td>
  <td>20</td>
  <td>20</td>
  <td></td>
  <td></td>
  <td></td>
</tr>
<tr>
  <td></td>
  <td>芦屋市</td>
  <td>3</td>
  <td></td>
  <td></td>
  <td>3</td>
  <td></td>
</tr>

前後に<table><tbody>タグを書き込めば、とりあえず表の形になります:
学校数 給食実施校 未実施校 備考
完全給食 ミルク給食
神戸市 85 2* 83 75校で弁当販売 *は夜間中学
阪神 尼崎市 20 1** 19 **は夜間中学での補食給食
西宮市 20 20
芦屋市 3 3

(あ! こりゃ、例がまずかった! 兵庫県内では学校数で53%、自治体(設置者)数で75%が中学校完全給食をやってます。ミルク給食だけの神戸とか実施していない芦屋なんかは少数派なのです)

行や列ごとに背景色など書式をつけたり、数字のセルだけ右寄せにしたり...など<td>内への書式指定はawkで半自動化できるはず。それは後ほどアップします。

-

2010年6月15日

行連結sedスクリプト

私がつくっているのは新聞形式なので、一つ一つの記事は短いのです。そのため、原稿をメール本文で遣り取りすることがあります。

また、記事の中の段落も短く、メールサーバーでのSMTPの行長制限(1,000chracters)を超えることもあまりないのですが、メーラーが自動的に78桁以下に改行して送信してくることもあるし、古くからインターネットを使っている著者が、手ずから改行して送ってくれることもあります。

でも、それを組版するには、段落内の行を連結し直さなくてはなりません。もともと短い記事だから、手作業でもそれほど手間ではないのですが、ものぐさな私はそれをsedにさせてます。


★2011.11.18訂正:「P」と「D」を実行しないと、各段落の1行目が処理されなようです。そういえばはじめてこのスクリプを書いた時、この二つのコマンドを使った記憶があるのですが、長い間使ってなくて、思い出しながら書いたら、案の定、抜けてました。


スクリプトA: 段落冒頭の字下げを全角空白でしてある原稿用
:loop
$!N
s/\(.\+\)\n\([^ ]\+\)/\1\2/
t loop
P
D

 は全角空白です。

スクリプトB: 段落冒頭の字下げをしないで、空行で段落を区切ってある原稿用
:loop
$!N
s/\(.\+\)\n\(.\+\)/\1\2/
t loop
P
D

ほんとのことを言うと、MacOSXを仕事に使いだしてから、sedはあまり使わなくなっていたんです。この行連結スクリプトは、ずーっと以前(10年近く前?)、FreeBSDで編集作業をしていたころ使っていたもの。

最近になって、紙の新聞に加えてWeb版を公開することになり、そうなると、元の記事からWeb用にふさわしい表記に書き換える作業(全角数字を半角数字に書き換えるなど)が出てきました。それで、sedの出番となり、そのついでに記憶の底から引き出してきたのがこの行連結スクリプトです。

googleで検索してみても、行連結のsedスクリプトは見つけにくいので、ひょっとしたら誰かの役に立つかもと、ここに掲載する次第です。

2010年6月13日

Macのsedはやっぱり変! でも『ネコのマロン...』は面白そう

MacOSXのsedは、まだマルチバイト文字がうまく扱えないようです。

このsedでも、

 script_0  y/1234567890/1234567890/g

は、環境変数LANGがja_JP.UTF-8にセットされていればちゃんと動きますし、modernな正規表現も「E」オプションをつければ使えるのですが、下のtest.txtを
 script_1  s/ネ[^、]+/NEKO/g
で編集してみると... 元のままのテキストが出力されるだけ。patternがマッチしていないようです。

test.txt
[A]
『ネコのマロン、参院選に立つ。』の著者さん、編集担当さんには
鳩山首相の辞任はとんだとばっちりではないですか?

今回の参議院選挙に間に合わせて公職選挙法を改正してネット選挙を
解禁することはすべての党派で一致していたのに、辞任のドタバタで
会期を延長しないと改正が間に合わない...

ところで、ネット選挙が解禁されても、私がつくっているような印刷物での
選挙は、従来どおりほとんどできないままになるようです。

[B]
『ネコのマロン,参院選に立つ。』の著者さん、編集担当さんには

[C]
『ネコのマロン、参院選に立つ。』の著者さん,編集担当さんには


そこで、マルチバイト文字である「、」をシングルバイト文字の「,」に替えてみると...
 script_2  s/ネ[^,]+/NEKO/g

編集結果は:
[A]
『NEKO
鳩山首相の辞任はとんだとばっちりではないですか?

今回の参議院選挙に間に合わせて公職選挙法を改正してNEKO
解禁することはすべての党派で一致していたのに、辞任のドタバタで
会期を延長しないと改正が間に合わない...

ところで、NEKO
選挙は、従来どおりほとんどできないままになるようです。

[B]
『NEKO,参院選に立つ。』の著者さん、編集担当さんには
[C]
『NEKO,編集担当さんには

変な文章になりますが、これは意図どおり。script_2は正しく作動しました。


私が編集しているのは日本語テキストなので、MacOSXのsedがこの有様では仕事になりません。(あ、書き忘れましたが、この記事でのスクリプトや処理対象テキストのエンコードはUTF-8です)。

そこで、GNUのsedをインストールしてみました。GNU sedでは「+」はエスケープしないといけないので、スクリプトは、
 script_3  s/ネ[^、]\+/NEKO/g

編集結果は:
[A]
『NEKO、参院選に立つ。』の著者さん、編集担当さんには
鳩山首相の辞任はとんだとばっちりではないですか?

今回の参議院選挙に間に合わせて公職選挙法を改正してNEKO
解禁することはすべての党派で一致していたのに、辞任のドタバタで
会期を延長しないと改正が間に合わない...

ところで、NEKO、私がつくっているような印刷物での
選挙は、従来どおりほとんどできないままになるようです。

[B]
『NEKO、編集担当さんには
[C]
『NEKO、参院選に立つ。』の著者さん,編集担当さんには
はい、これも意図どおり (^_^)y これなら仕事に使えます。


なお、『ネコのマロン、参院選に立つ。』(植松眞人著, 保育社から7月上旬発売予定)は、ネット選挙が主なテーマじゃなくて、今まで政治や選挙に興味がなかったり敬遠していた人々、または政治に興味を持ち始めた学生たちに、選挙のしくみをネコのマロンを通して楽しみながら知ってもらいたい...と企画されたのだそうです。

選挙や投票とは何か、参院選の任期のこと、など基本的なことから説明します、とのこと。つまり、私が上のtest.txtで書いたようなことは心配ないということです。


この本について詳しくは「ほいくしゃの本屋さん」サイトのページをご覧ください。
http://hoikusha-shop.jp/SHOP/9784-586-08510-1.html



なお、なお、GNU sedはオリジナルのソースからコンパイルしました。4.2.1版なのですが、MacOSX 10.6のXcodeであっさりインストールできましたよ。
MacPortとかFinkとかを使おうかと思ったのですが、それ自体がちょっと大層な(かつて、OSX 10.4で使った折の印象)システムなのでやめました。それに、MacPortだとsedをインストールするにはgettextとlibiconvが必要、gettextはexpat・libiconv・ncursesの3つが必要で、さらにncursesはncurseswが必要、戻ってlibiconvにはgperfが必要.......こんな風に芋蔓式にインストールするものが増えていくのも難儀なことでした(これはFinkでも、*BSDやLinuxのパッケージ管理システムでも同じですね)。今回、sedのソースだけでコンパイルできたってことは.... あの芋蔓はいったい (@_@;;