FFMPEG에서 파일을 분할하는 방법은 매우 다양하며, 다양한 기준에 따라 파일을 나눌 수 있다. 이 장에서는 파일 분할의 여러 가지 방법을 다루며, 명령어와 함께 그 원리를 설명한다.
시간 기반 파일 분할
비디오 또는 오디오 파일을 특정 시간대별로 분할할 수 있다. 이를 위해 -ss
와 -t
옵션을 사용하여 원하는 시작 시간과 지속 시간을 설정한다.
ffmpeg -i input.mp4 -ss 00:00:00 -t 00:05:00 -c copy output1.mp4
이 명령어는 input.mp4
파일을 처음부터 5분 동안의 비디오만 output1.mp4
로 복사하는 것이다. 중요한 점은 -c copy
를 사용하여 인코딩 없이 파일을 복사하는 것이므로, 속도가 빠르고 품질 손실이 없다.
시간 분할의 수학적 표현
비디오 파일을 시간적으로 분할할 때, 이를 수학적으로 표현할 수 있다. 비디오의 전체 길이를 T라고 할 때, t_1와 t_2가 시작 시간과 끝 시간이라면, 분할된 비디오의 길이는 다음과 같이 표현된다.
여기서 \Delta t는 분할된 비디오의 길이를 의미한다.
프레임 기반 파일 분할
시간 대신 특정 프레임 단위로도 파일을 분할할 수 있다. FFMPEG에서는 -vf
필터 옵션을 통해 프레임을 제어한다. 예를 들어, 초당 프레임 수(Frames per second, FPS)를 기준으로 분할할 수 있다.
ffmpeg -i input.mp4 -vf "select='gte(n\,300)'" -c copy output2.mp4
이 명령어는 300번째 프레임 이후의 비디오를 output2.mp4
로 복사하는 것이다. n
은 현재 프레임 번호를 나타낸다.
프레임 기반 분할의 수학적 모델
영상 파일은 보통 초당 프레임 수로 구성된다. 프레임 기반으로 파일을 분할할 때는, 특정 프레임 번호 n에서부터 분할할 수 있다. 총 프레임 수를 N로 두고, t는 시간, f는 프레임 속도(FPS)를 나타낸다면, 특정 프레임에서 분할된 비디오의 시작 시간은 다음과 같다.
이때 n은 시작하는 프레임 번호이고, f는 초당 프레임 수(FPS)이다.
크기 기반 파일 분할
파일 크기를 기준으로 분할할 수 있다. 이 경우, FFMPEG은 자체적으로 파일 크기를 제한하는 옵션을 제공하지 않지만, 이를 위한 다양한 스크립트나 방법을 사용할 수 있다. 예를 들어, 파일 크기를 기준으로 일정 크기마다 파일을 분할하려면, split
명령어를 사용하는 방법이 있다.
다음은 Linux에서 파일을 크기 기반으로 분할하는 예시이다.
split -b 100M input.mp4 output_prefix
이 명령어는 input.mp4
파일을 100MB씩 분할하여, 파일 이름이 output_prefixaa
, output_prefixab
등으로 나뉜다. 이후 각 분할된 파일은 다시 FFMPEG으로 처리하거나 병합할 수 있다.
파일 크기 분할의 수학적 표현
파일 크기를 기반으로 분할할 때, 파일의 총 크기를 S, 분할하려는 파일의 크기를 s라고 하자. 그렇다면, 총 몇 개의 분할 파일이 나올지를 계산하는 식은 다음과 같다.
여기서 n은 분할된 파일의 개수를 의미하며, \lceil \cdot \rceil는 올림 연산을 뜻한다. 이를 통해 전체 파일 크기에 따라 몇 개의 파일로 분할할지를 예측할 수 있다.
키 프레임 기반 파일 분할
비디오 파일을 분할할 때, 특정 키 프레임(Key Frame)을 기준으로 분할할 수 있다. 키 프레임은 비디오 압축 방식에서 중요한 역할을 하며, 이를 기준으로 분할하면 자연스러운 비디오 전환이 가능하다.
ffmpeg -i input.mp4 -c copy -f segment -segment_frames 1000 -reset_timestamps 1 output%03d.mp4
이 명령어는 input.mp4
파일을 1000개의 프레임 단위로 분할하여 각 분할 파일의 이름을 output001.mp4
, output002.mp4
등으로 생성한다.
키 프레임 분할의 수학적 모델
키 프레임을 기준으로 파일을 분할하는 경우, 특정 구간에서 첫 번째 키 프레임을 찾는 것이 중요하다. 이때, n번째 키 프레임에서 비디오를 분할한다면, 다음과 같은 수식으로 나타낼 수 있다.
여기서 \mathbf{k}_n은 n번째 키 프레임을 의미하며, key_frame
함수는 특정 프레임이 키 프레임인지 여부를 반환하는 함수이다. 이를 통해 특정 키 프레임에서 자연스러운 비디오 분할이 가능해진다.
장면 기반 파일 분할
장면 전환을 감지하여 비디오 파일을 분할할 수도 있다. 이 방법은 주로 장면 변화가 극명한 비디오에서 유용하며, FFMPEG의 -vf
필터에서 select
옵션을 활용하여 장면 변화를 감지할 수 있다.
ffmpeg -i input.mp4 -vf "select='gt(scene\,0.4)'" -vsync vfr output%d.mp4
이 명령어는 장면 변화가 40% 이상 감지된 지점에서 비디오를 분할하여 output1.mp4
, output2.mp4
등의 파일을 생성한다. 여기서 scene
값은 장면 전환의 민감도를 조절하며, 값이 높을수록 더 큰 변화에서만 장면이 분할된다.
장면 기반 분할의 수학적 모델
장면 전환을 감지하여 비디오를 분할할 때, 영상의 프레임별 픽셀 값 변화 정도를 분석하여 장면 변화를 감지한다. 특정 장면에서의 프레임 변화를 \Delta P라고 할 때, \Delta P가 설정된 임계값 \theta보다 클 경우, 그 지점에서 비디오가 분할된다.
여기서 I(i,j,t)는 시간 t에서 픽셀 (i,j)의 밝기값을 의미하며, \Delta P는 두 프레임 간의 차이를 나타낸다. 이 값이 임계값 \theta를 넘으면, 장면 변화가 발생했다고 판단한다.
파일 분할 자동화
FFMPEG은 다양한 방식으로 파일 분할을 자동화할 수 있다. 예를 들어, 비디오를 일정 시간 간격으로 분할하려는 경우, -f segment
옵션을 사용할 수 있다.
ffmpeg -i input.mp4 -c copy -f segment -segment_time 60 output%03d.mp4
이 명령어는 input.mp4
를 60초마다 분할하여 파일을 생성한다. 각 파일은 output001.mp4
, output002.mp4
등의 형식으로 저장된다. -segment_time
옵션은 분할 시간 간격을 지정하며, 이 옵션을 사용하면 비디오가 자동으로 여러 파일로 나뉜다.
자동 분할의 수학적 표현
시간 간격을 기준으로 자동 분할하는 경우, 총 시간 T를 일정 간격 \Delta t로 나누어 분할할 수 있다. 분할된 파일의 개수는 다음과 같다.
여기서 n은 생성된 분할 파일의 개수를 나타내며, \Delta t는 분할 간격(초)을 의미한다.
파일 분할 후 재병합
분할된 파일을 다시 하나로 병합하는 것도 가능하다. 이를 위해 concat
명령어를 사용하여 여러 파일을 하나로 병합할 수 있다.
먼저, 병합할 파일 목록을 텍스트 파일에 작성한다.
file 'output1.mp4'
file 'output2.mp4'
file 'output3.mp4'
그 후, 다음 명령어를 통해 이 파일들을 하나로 병합한다.
ffmpeg -f concat -safe 0 -i filelist.txt -c copy merged_output.mp4
병합의 수학적 모델
파일 병합은 각각의 분할 파일을 시간 축에서 다시 연결하는 과정이다. 만약 각각의 분할 파일의 길이가 T_1, T_2, \dots, T_n이라면, 병합된 파일의 총 길이는 다음과 같이 계산된다.
이때 T_{\text{merged}}는 병합된 파일의 총 시간을 나타낸다.