何日か経ちましたし、もういいですよね……

課題

お題:ゴールデンウイークシェル芸問題 | 上田ブログ

>
     1から100まで数字が書いてあるansというファイルを作り、ansの中から素数でない数をワンライナーだけで消し去ってください。(ansの中身を書き換えるということです。forもwhileもなしで、コマンドはパイプでつないで。)
1
% seq 100 > ans

はじめの回答

1
% cat ans | factor | sed 's/://g' | awk 'NF==2{print $1}' | cat > ans

課題

awkのバッファリングに依存しており、問題の100件程度では問題ないのですが、件数が多くなると壊れます。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
% seq 100000 > ans
% tail ans
13367
13381
13397
13399
13411
13417
13421
13441
13451
13

また、Cシェル系(csh/tcsh/zsh)ではうまくいきましたが、Bシェル系(sh/Bash)ではうまくいきませんでした。

別解

TL上には様々な解が出ていましたが、自分はヒアドキュメントを生成して評価する、という手法で解決しました。

1
cat ans | factor | sed 's/://g' | awk 'BEGIN{print "cat <<EOS>ans"}NF==2{print $1}END{print "EOS"}' | sh

こちらはcsh/tcsh/zsh/sh/Bashで確認済みです。
※模範解答は moreutilsの sponge コマンド使うやつですよね