.ts
파일 목록이 있습니다.
out1.ts ... out749.ts out8159.ts out8818.ts
이 모든 파일의 총 지속 시간 (실행 시간)을 어떻게 얻을 수 있습니까?
.ts
파일 목록이 있습니다.
out1.ts ... out749.ts out8159.ts out8818.ts
이 모든 파일의 총 지속 시간 (실행 시간)을 어떻게 얻을 수 있습니까?
답변:
나는 .ts
여기에 없지만이 작동합니다 .mp4
. ffprobe
(의 일부 ffmpeg
)를 사용 하여 시간을 초 단위로 가져옵니다. 예 :
ffprobe -v quiet -of csv=p=0 -show_entries format=duration Inception.mp4
275.690000
.mp4
현재 디렉토리의 모든 파일에 대해 :
find . -maxdepth 1 -iname '*.mp4' -exec ffprobe -v quiet -of csv=p=0 -show_entries format=duration {} \;
149.233333
130.146667
275.690000
다음 사용 paste
하는 출력을 통과 에 bc
초 총 시간을 얻을 :
find . -maxdepth 1 -iname '*.mp4' -exec ffprobe -v quiet -of csv=p=0 -show_entries format=duration {} \; | paste -sd+ -| bc
555.070000
따라서 .ts
파일의 경우 다음을 시도 할 수 있습니다.
find . -maxdepth 1 -iname '*.ts' -exec ffprobe -v quiet -of csv=p=0 -show_entries format=duration {} \; | paste -sd+ -| bc
여기에있는 비디오 파일에서 작동하는 다른 도구는 다음 exiftool
과 같습니다.
exiftool -S -n Inception.mp4 | grep ^Duration
Duration: 275.69
exiftool -q -p '$Duration#' Inception.mp4
275.69
.mp4
현재 디렉토리에있는 모든 파일의 총 길이 :
exiftool -S -n ./*.mp4 | awk '/^Duration/ {print $2}' | paste -sd+ -| bc
555.070000000000
exiftool -q -p '$Duration#' ./*.mp4 | awk '{sum += $0}; END{print sum}'
555.070000000000
또한 출력을 다른 명령으로 파이프하여 합계를로 변환 할 수도 있습니다 . 여기DD:HH:MM:SS
에서 답변을 참조 하십시오 .
또는에 exiftool
내부 ConvertDuration
를 사용하십시오 (상대적으로 최신 버전이 필요합니다).
exiftool -n -q -p '${Duration;our $sum;$_=ConvertDuration($sum+=$_)
}' ./*.mp4| tail -n1
0:09:15
ffprobe
전에 그 트릭을 보지 못했다 .
paste
와 bc
! awk
말 보다 훨씬 더 깨끗 합니다.
bc
임의의 정밀도를 수행 하지만 한 가지 단점은 ...| paste -sd+ - | bc
일부 bc
구현 에서 라인 크기 제한에 도달하거나 (예 : seq 429 | paste -sd+ - | bc
OpenSolaris에서 실패 bc
) 다른 메모리에서 모든 메모리를 사용할 가능성이 있다는 것입니다.
avprobe
(이과 충돌하기 때문에 prolly 아치 REPOS에서이 ffmpeg
) 그래서 그것을 ATM을 시도 할 수 있지만,이처럼 실행하면 그것은 당신에게 파일의 지속 시간을 제공 않습니다 avprobe -show_format_entry duration myfile.mp4
나 avprobe -loglevel quiet -show_format_entry duration myfile.mp4
? 이 명령 중 하나가 파일 지속 시간이있는 단일 출력 줄을 제공해야한다고 생각합니다. 그래도 확실하지 않습니다.
ffmpeg
총 시간 (초)으로 시간 초과를 사용 하고 인쇄합니다.
times=()
for f in *.ts; do
_t=$(ffmpeg -i "$f" 2>&1 | grep "Duration" | grep -o " [0-9:.]*, " | head -n1 | tr ',' ' ' | awk -F: '{ print ($1 * 3600) + ($2 * 60) + $3 }')
times+=("$_t")
done
echo "${times[@]}" | sed 's/ /+/g' | bc
설명:
for f in *.ts; do
".ts"로 끝나는 각 파일을 반복합니다.
ffmpeg -i "$f" 2>&1
출력을 stderr로 리디렉션
grep "Duration" | grep -o " [0-9:.]*, " | head -n1 | tr ',' ' '
시간을 분리
awk -F: '{ print ($1 * 3600) + ($2 * 60) + $3 }'
시간을 초로 변환
times+=("$_t")
배열에 초를 추가합니다
echo "${times[@]}" | sed 's/ /+/g' | bc
각 인수를 확장하고 공백을 바꾸고 bc
일반적인 Linux 계산기로 파이프합니다.
간소화 jmunsch의 대답 @ 및 사용 paste
단지에서 배운 I @ SLM의 답변을 ,이 같은 끝낼 수 :
for i in *.ts; do LC_ALL=C ffmpeg -i "$i" 2>&1 | \
awk -F: '/Duration:/{print $2*3600+$3*60+$4}'; done | paste -sd+ | bc
jmunsch와 마찬가지로 ffmpeg
지속 시간을 인쇄하여 누락 된 출력 파일에 대한 오류를 무시하고 대신 지속 시간 줄의 오류 출력을 검색하는 데 사용하고 있습니다. ffmpeg
표준 C 로캘로 강제 설정된 로캘의 모든 측면을 호출 하므로 현지화 된 출력 메시지에 대해 걱정할 필요가 없습니다.
다음 awk
으로 그의 대신 단일을 사용하고 grep | grep | head | tr | awk
있습니다. 이 awk
호출은을 포함하는 (희망적으로 고유 한) 행을 찾습니다 Duration:
. 구분 기호로 콜론을 사용하면 해당 레이블은 필드 1, 시간은 필드 2, 분은 3 분, 초는 필드 4입니다. 초 뒤의 쉼표는 my를 방해하지 않지만 awk
누군가 문제가있는 경우 와 tr -d ,
사이의 파이프 라인에를 포함 할 수 있습니다 .ffmpeg
awk
이제는 slm에서 나온 부분입니다. paste
개행을 더하기 기호로 바꾸는 데 사용 하지만 후행 줄 바꿈에는 영향을 미치지 않습니다 ( 이 답변 의 이전 버전tr \\n +
에서와 달리 ). 그것은 식을 제공 할 수있는 합계 식을 제공합니다 .bc
date
시간과 같은 형식을 처리하는 데 사용하는 slm의 아이디어에서 영감을 얻은 다음은 소수 부분을 사용하여 결과 초를 일, 시간, 분 및 초로 형식화하는 버전입니다.
TZ=UTC+0 date +'%j %T.%N' --date=@$(for i in *.ts; do LC_ALL=C \
ffmpeg -i "$i" 2>&1 | awk -F: '/Duration:/{print $2*3600+$3*60+$4}'; done \
| paste -sd+ | bc) | awk '{print $1-1 "d",$2}' | sed 's/[.0]*$//'
내부 부품 $(…)
은 이전과 동일합니다. @
문자를 표시로 사용하여 , 우리는 이것을 1970 년 1 월 1 일 이후의 초 수로 사용합니다. 결과 "날짜"는 연중 일, 시간 및 나노초로 형식화됩니다. 0 초의 입력이 이미 1970 년의 1 일로 이어지기 때문에 1 년을 뺀 것입니다. 저는 0에서 시작하는 연도의 카운트를 얻는 방법이 없다고 생각합니다.
마지막은 sed
별도의 후행 제로를 제거한다. 이 TZ
설정은 UTC 사용을 강요하여 일광 절약 시간이 실제로 큰 비디오 컬렉션을 방해하지 않도록해야 합니다. 1 년 분량의 비디오가 있다면이 방법은 여전히 작동하지 않습니다.
.ts
확장명에 익숙하지 않지만 파일 형식을 가정 ffmpeg
하여 파일의 지속 시간을 식별하는 데 사용할 수 있다고 가정 합니다.
$ ffmpeg -i some.mp4 2>&1 | grep Dura
Duration: 00:23:17.01, start: 0.000000, bitrate: 504 kb/s
그런 다음 지속 시간 만 선택하여이 출력을 분할 할 수 있습니다.
$ ffmpeg -i some.mp4 2>&1 | grep -oP "(?<=Duration: ).*(?=, start.*)"
00:23:17.01
이제 파일을 반복하고 이러한 지속 시간 값을 수집하는 방법이 필요합니다.
$ for i in *.mp4; do
ffmpeg -i "$i" 2>&1 | grep -oP "(?<=Duration: ).*(?=, start.*)"; done
00:23:17.01
00:23:17.01
00:23:17.01
참고 : 여기 내 예를 들어 나는 단지 내 샘플 파일을 복사 some.mp4
하고 이름 1.mp4
, 2.mp4
하고 3.mp4
.
다음 스 니펫은 위에서부터 지속 시간을 가져 와서 초로 변환합니다.
$ for i in *.mp4; do
dur=$(ffmpeg -i "$i" 2>&1 | grep -oP "(?<=Duration: ).*(?=, start.*)");
date -ud "1970/01/01 $dur" +%s; done
1397
1397
1397
$dur
파일을 반복하면서 지속 시간을 가져와 변수에 넣습니다 . date
그런 다음 이 명령을 사용하여 Unix 신기원 (1970/01/01)을 사인하는 초 수를 계산합니다. 위의 date
명령 은 다음과 같이 구분되어보다 쉽게 볼 수 있습니다.
$ date -ud "1970/01/01 00:23:17.01" +%s
1397
참고 :date
이 방식으로 사용 하면 모든 파일의 지속 시간이 24 시간 미만 (예 : 86400 초) 인 경우에만 작동합니다. 더 긴 시간을 처리 할 수있는 것이 필요한 경우이를 대안으로 사용할 수 있습니다.
sed 's/^/((/; s/:/)*60+/g' | bc
예
$ echo 44:29:36.01 | sed 's/^/((/; s/:/)*60+/g' | bc
160176.01
그런 다음 for
루프 의 출력을 가져 와서 각 번호 사이에 부호를 paste
포함 하는 명령 으로 실행할 +
수 있습니다.
$ for i in *.mp4; do
dur=$(ffmpeg -i "$i" 2>&1 | grep -oP "(?<=Duration: ).*(?=, start.*)");
date -ud "1970/01/01 $dur" +%s; done | paste -s -d+
1397+1397+1397
마지막으로 이것을 명령 줄 계산기로 실행 bc
하여 요약합니다.
$ for i in *.mp4; do
dur=$(ffmpeg -i "$i" 2>&1 | grep -oP "(?<=Duration: ).*(?=, start.*)");
date -ud "1970/01/01 $dur" +%s; done | paste -s -d+ | bc
4191
모든 파일의 총 지속 시간 (초). 물론 필요한 경우 다른 형식으로 변환 할 수도 있습니다.
date
경우 질식 할 수 있습니다.ffmpeg -i some.mp4 2>&1 | grep -oP "(?<=Duration: ).*(?=, start.*)"
26:33:21.68
paste
내 관심. 내가 추측이 java -classpath $(find -name \*.jar | paste -sd:)
될 것입니다 매우 내가 과거에이 사용했던 해킹을 고려, 나에게 유용합니다.
paste
내가 가장 좋아하는 명령입니다 8-)
허용되는 답변을 없애고 고전적인 UNIX 리버스 툴을 사용하십시오.
{ find . -maxdepth 2 -iname '*.mp4' -exec ffprobe -v quiet -of csv=p=0 \
-show_entries format=duration {} \; ; printf '+\n60\n*\np'; } | dc
783.493000
즉 : 그것을 적용 +
하고 p
파이핑 dc
하면 합계를 얻을 수 있습니다.
$ find -iname '*.ts' -print0 |\
xargs -0 mplayer -vo dummy -ao dummy -identify 2>/dev/null |\
perl -nle '/ID_LENGTH=([0-9\.]+)/ && ($t += $1) && printf "%02d:%02d:%02d:%02d\n",$t/86400,$t/3600%24,$t/60%60,$t%60'
MPlayer가 설치되어 있는지 확인하십시오 .
글쎄,이 모든 솔루션에는 약간의 작업이 필요합니다. 내가 한 일은 매우 간단했습니다. 1)
원하는 폴더로 이동하고 마우스 오른쪽 버튼을 클릭-> 다른 응용 프로그램으로 열기
그런 다음 VLC 미디어 플레이어를 선택하고
여기 예입니다
툴바 바로 아래에서 볼 수 있으며, 재생 목록 [10:35:51]이 작성되어 있으므로 폴더에는 총 비디오 시간이 10 시간 35 분 51 초입니다.