avconv の「選択」フィルターを使用してビデオをセグメント化し、入力ファイルから特定の範囲のフレームのみを抽出しようとしています。例として、3000 フレーム (つまり 50 秒) の input.mp4 という 60 fps ビデオ ファイルがあり、実行したとします。
avconv -i input.mp4 -vf "select='lt(n,2000)'" output1.mp4
avconv -i input.mp4 -vf "select='gte(n,2000)'" output2.mp4
私が期待するのは、output1.mp4 には input.mp4 の最初の 2000 フレーム (および持続時間は ~33 秒) があり、output2.mp4 には最後の 1000 フレーム (および持続時間は ~17 秒) があることです。
実行してフレームを数えます
avconv -i video.mp4 -vcodec copy -an -f null /dev/null 2>&1 | grep 'frame='
「frame」に割り当てられた値を確認します。
私が実際に得たのは、output1.mp4 には 2000 フレームがあり、約 33 秒続くが、output2.mp4 には 2999 フレームがあり、それでも約 50 秒続くということです。output2.mp4 を開くと、ビデオの最初の 2000 フレームが、実際には入力の 2000 番目のフレームの単なる繰り返しであることがわかります。つまり、最初の 2000 フレームは正しくフィルタリングされているように見えますが、受け入れられたフレームの最初のものに置き換えられています。 .
これはptsの問題ではありません。avprobe を使用して、パケット数とその相対ポイントを確認します。
avprobe -show_packets output2.mp4
echo $(avprobe -show_packets output2.mp4 2>/dev/null | grep PACKET | wc -l)/2 | bc
実際には 2999 個のパケットがあることがわかります。
私は何を間違っていますか?
副次的な質問:
- 私が何か間違ったことをしていると仮定すると、output2.mp4 に完全な 3000 ではなく 2999 が含まれているのはなぜですか?
- フィルターで「gte」関数を使用しても「gt」関数を使用しても、動作は変わりません。それはなぜでしょうか?