区切り文字のない次の形式の長い一連のURLがあります。
http://example.comhttp://example.nethttp://example.orghttp://etc...
各URLをラップしたいです。私はsedを使って "http://"のすべてのインスタンスを "\nhttp://"に置き換えることによってこれをやろうとしています。
sed 's_http://_\nhttp://_g' urls.txt
ただし、分割エラー(メモリ違反)が発生します。ファイルの絶対サイズ(100 GB以上)のため、sedがいくつかの制限を超えたと推測できます。
処理のためにファイルを複数の小さなファイルに分割できますが、「http://」のすべてのインスタンスはそのまま残す必要があります。
もっと良い方法がありますか?
答え1
これにより、awk
一度に大量のテキストを読み取ることを回避できます。
awk -vRS='http://' -vORS='\nhttp://' 1 urls.txt > urlsperline.txt
成功するかどうかは、使用されている実装によって異なりますawk
。たとえば、うまくgawk
動作しますが、mawk
競合が発生します。
答え2
これにより操作が実行されます。
perl -pe 'BEGIN { $/ = "//" } s!(?=http://\z)!\n!' urls.txt
設定として$///
、改行で終わるように行定義を変更しました。これにより、Perlは一度に1つのURLを読み取ります。 URLに//
スキームの後を除いては含まれない可能性がありますが、含めても構いません。正規表現は偽の改行を追加するのを防ぎます。
最初のURLの前に空白行を追加したくない場合は、次のようにします。
perl -pe 'BEGIN { $/ = "//"; print scalar <> } s!(?=http://\z)!\n!' urls.txt
ベンチマークを試してより高速であることを確認できますs!http://\z!\nhttp://!
。それらは同じです。/g
「ライン」ごとに1つの一致がある可能性があるため、交換するときにこのフラグは必要ありません。
答え3
:
ファイルを分割するには、aのすべての項目を改行文字に変更します。- 変える
http
行末で- 改行文字の後に
http:
次の行が追加されます。
- 一度繰り返すと、偶数行と奇数行の両方が更新されます。
手順は次のとおりです。
tr ':' '\n' | sed -e '/http$/{N;s/http\n/\nhttp:/}' | sed -e '/http$/{N;s/http\n/\nhttp:/}'
で始まらない行があることを確認し、
http://
行番号を出力してください。 :このURLに存在しない場合にのみ適用されますhttp
。grep -nv '^http://'