木谷 公哉さんのプロフィール写真

Perl を使いたいなら、すでに回答があるようにファイルをバイナリで読み込んで先頭の3バイト以外を別ファイルに書き出すのが簡単です。

dd コマンドをつかうのが楽だと思います。

バイナリファイルの先頭バイトをカットする方法 - asakawajunyaのブログ

にあるように

dd if=元ファイル bs=1 skip=3 of=出力先ファイル

でいけますよ〜

追記(2019–10–23)

とか無責任なことをいっていた時期もありました。実際に bs=1 skip=3 の設定でやると時間がかかりすぎて話になりません。約 0.044% (185,836,413 / 4,194,304,000) を処理するのに 16分とかかかっていましたので。そこで標準コマンドでやるという限定のなかでいくつか試してみました。

検証環境:MacBook Pro 15inch (2016) , Intel Core i7 2.7Ghz クアッドコア、メモリ16GB

参考:Best way to remove bytes from the start of a file?

まずは 先頭3バイトに123というデータの入った 4GBのファイルを作成します。

Hex Friend というバイナリエディタでみると、先頭の3バイトに123が入っているのがわかりますよね!

なお、このファイルの作成方法は今回の先頭3バイトを切り出す最速の方法を使いました。そこは一番最後に説明します。

方法1)bs=3 skip=1(遅すぎ〜)

  • dd if=dd-4gb-test bs=3 skip=1 of=出力ファイル名

まぁ3倍速ですね。3バイトごと読み込んで1つスキップするので4バイト目から 3バイトずつ書き込むぜ!って感じ。実際に途中までやってみましたが、遅すぎて却下。

方法2)tail コマンドをつかう(まぁまぁ)

  • tail -c +4 dd-4gb-test > 出力ファイル名

のように先頭 4バイト目から書き込むぜ〜って感じ。まぁ結構速くなりました。とはいえ、6分46分かかりましたので、まだまだ遅いです。

方法3)dd と cat の組み合わせ(超高速)

  • {dd bs=3 skip=1 count=0; cat; } <dd-4gb-test > 出力ファイル名

12 秒(何度かすると 9秒〜12秒ぐらい)しか掛かりませんでした。この手法は標準入力にファイルをいれて、ddコマンドで 3バイトスキップして4バイト目にセットしコピーはしないでおく。その状態で cat コマンドで出力して、その結果を保存するというもの。つまりコピーはcatコマンドでやっちゃえって感じ。

のように容量は3バイト少なくなっていて、先頭の3バイトが消えています。

デモデータの作成方法

  • echo -n 123 > 3byte-file

で3バイト(123)の入ったファイルを作成します。

  • dd if=/dev/zero of=dd-4gb bs=1024k count=4000

4194304000 bytes transferred in 2.143140 secs (1957083461 bytes/sec)

な感じで2秒ほどで 4GBのファイルを作成ます。

  • {dd bs=3 skip=1 count=0; cat; } < dd-4gb > dd-4gb-3bytes-file

のように先頭3バイトを削除したデータを作成します。

  • cat 3byte-file dd-4gb-3bytes-file > dd-4gb-test

のように2つのファイルを連結します。これで dd-4gb-test が出来上がりということです。

この質問に対する他の2件の回答を表示