Wie bekomme ich die Videodauer in Sekunden?


69

Wie kann ich die Videodauer in Sekunden ermitteln?

Was ich versucht habe:

ffmpeg -i file.flv 2>&1 | grep "Duration"
  Duration: 00:39:43.08, start: 0.040000, bitrate: 386 kb/s


mediainfo file.flv | grep Duration
Duration : 39mn 43s

Das, was nahe kommt, aber es ist nicht so genau, 2383 ist 39,71 Minuten

ffmpeg -i file.flv 2>&1 | grep "Duration"| cut -d ' ' -f 4 | sed s/,// | sed 's@\..*@@g' | awk '{ split($1, A, ":"); split(A[3], B, "."); print 3600*A[1] + 60*A[2] + B[1] }'
2383

Antworten:


36

Um Minuten zu erhalten, müssen Sie 2383 Sekunden durch 60 teilen.

39.7167

und multiplizieren Sie dann den Bruchteil .7167 mit 60, um die verbleibenden Sekunden zu erhalten.

43.002

Es sind also 39 Minuten und 43 Sekunden. Die Anwendung scheint Ihnen einen genauen Wert zu liefern.


96

Einfach ffprobedirekt verwenden. Keine Notwendigkeit für sed, grepusw. Es gibt mehrere "Dauern", die Sie erwerben können (abhängig von Ihrer Eingabe).

Formatdauer (Container)

$ ffprobe -v error -show_entries format=duration \
  -of default=noprint_wrappers=1:nokey=1 input.mp4

30.024000

Durch Hinzufügen der -sexagesimalOption wird das Zeiteinheitsformat HOURS: MM: SS.MICROSECONDS verwendet:

0:00:30.024000

Dauer des Videostreams

$ ffprobe -v error -select_streams v:0 -show_entries stream=duration \
  -of default=noprint_wrappers=1:nokey=1 input.mp4
30.000000

Die obigen Befehle stammen aus FFmpeg Wiki: FFprobe Tips .

Mit ffmpeg

Möglicherweise müssen Sie die Eingabe vollständig dekodieren, wenn Sie feststellen, dass die Container- oder Stream-Dauer fehlt oder ungenau ist (möglicherweise aufgrund einer beschädigten oder abgeschnittenen Datei).

$ ffmpeg -i input.mp4 -f null -
  …
  frame= 1587 fps=0.0 q=0.0 Lsize=N/A time=00:01:03.48 bitrate=N/A

In diesem Beispiel time=00:01:03.48ist die Dauer:

Wie lange dies dauern wird, hängt natürlich von der Dekodierungskomplexität und -dauer Ihrer Eingabe sowie von den Fähigkeiten Ihres Computers ab.


Diese funktionieren nicht für .m2v Dateien haben Sie eine Lösung für sie als gut
utdev

@utdev Siehe ffmpegAbschnitt "Mit ".
Logan

Ihre dritte Lösung gibt mir eine falsche Zeit, mein Video eine Länge von 01.19.00 hat aber der Befehl gibt mir Zeit = 01: 09: 15.32, haben Sie eine Vermutung , warum dies geschieht
utdev

Sehr nützlich die Dauer des Media Streams. Danke.
Wir sind Borg

Bei Verwendung von avprobe unterscheiden sich die Parameter geringfügig: avprobe -v error -show_format_entry duration. \ Sample.mp4
Brad,

32

Wenn Sie haben ffmpeg, sollten Sie auch haben ffprobe:

ffprobe -i input.file -show_format | grep duration
ffprobe -i input.file -show_format -v quiet | sed -n 's/duration=//p'

Dies ergibt auch Sekundenbruchteile. Wenn dies ein Problem ist, können Sie es mit sed weiterverarbeiten.


Wie kann ich den Bruchteil von Sekunden entfernen?
Tina J

@TinaJ Pipe es einfach mit printf, wie | xargs printf %.0f- dies wird einen ganzzahligen Wert zurückgeben.
Ilia Rostovtsev

3

Um für mein ffmpeg-0.6.5-1.el6.rf.x86_64 nur das zweite ffprobe-Befehlsformat zu erhalten, ist:

ffprobe <file> -show_format 2>&1 | sed -n 's/duration=//p' 

Wie kann ich den Bruchteil von Sekunden entfernen?
Tina J

3

Lösung mit mplayer, der Sekunden direkt gibt:

mplayer -identify -frames 0 -vo null -nosound file.flv 2>&1 | awk -F= '/LENGTH/{print $2}'

2
mediainfo --Output='General;%Duration%' file.flv

Dies gibt die Dauer in Millisekunden als einen einzelnen ganzzahligen Wert aus. Keine Notwendigkeit für grep / cut / sed / ...


Danke - das war genau das, wonach ich gesucht habe. Kann unter MacOS mitbrew install mediainfo
Alex K

0

Ich bin auf das Problem gestoßen, dass einige Videodateien, mit denen ich gearbeitet habe, seltsame und inkorrekte Metadaten enthielten, und ich konnte mit Code und Tools wie ffmpeg, mp4box, ffprobe, mediainfo, mplayer, um die tatsächliche Dauer des Videos abzurufen.

Das Ermitteln der tatsächlichen Dauer des Videos war eine Voraussetzung für ein Projekt, an dem ich gearbeitet habe. Die einzige Möglichkeit, die ich gefunden habe, um es immer richtig zu machen, bestand darin, die Videodatei mit ffmpeg neu zu codieren und codierte Dateien zu zwingen, die Metadaten der Originaldatei zu ignorieren.

ffmpeg -i INPUT_FILENAME -acodec copy -vcodec copy -map_metadata -1 OUTPUT_FILENAME"

(Dies läuft möglicherweise schneller als erwartet. Ich war überrascht, dass die durchschnittliche Zeit für die Art des Inhalts und die von mir verwendete Umgebung 2 Sekunden betrug.)

... und dann mit einem Werkzeug Ihrer Wahl die Dauer abrufen. Ich mag mediainfo, btw: - "mediainfo FILE --Inform =" Video;% Duration% "gibt die Dauer in Millisekunden an.


Sie haben nicht mehr Informationen oder eine bessere Lösung angegeben als andere Antworten
Sam

0

Wenn Sie nur Metadaten abfragen müssen:

ffprobe -hide_banner -v quiet -show_streams -print_format flat video.mp4

[...]

streams.stream.0.duration="5221.146009"

[...]

So können Sie es analysieren:

while read -r; do
  if [[ "$REPLY" =~ ^streams\.stream\.([0-9])+\.duration=\"([^"]+)\"$ ]]; then
    echo -E Duration of stream "${BASH_REMATCH[1]}": "${BASH_REMATCH[2]}"
  fi
done < <(ffprobe -hide_banner -v quiet -show_streams -print_format flat video.mp4)

Wenn Sie jedoch die effektive Container-Dauer ermitteln möchten, müssen Sie sie dekodieren:

AV_LOG_FORCE_NOCOLOR=y ffmpeg -nostdin -hide_banner -nostats -loglevel info -i video.mp4 -f null -c copy - 2>&1 | tail -n 2

Das Dekodieren dauert einige Zeit, bis:

[...]

frame=130527 fps=53271 q=-1.0 Lsize=N/A time=01:27:01.12 bitrate=N/A speed=2.13e+03x
video:152014kB audio:40790kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: unknown

Dann können Sie es analysieren:

if [[ "$(AV_LOG_FORCE_NOCOLOR=y ffmpeg -nostdin -hide_banner -nostats -loglevel info -i video.mp4 -f null -c copy - 2>&1 | tail -n 2 | head -n 1)" =~ \ time=([0-9]+):([0-9]{2}):([0-9]{2})\.([0-9]+) ]]; then
  declare duration=0 us="${BASH_REMATCH[4]}" t
  for t in "${BASH_REMATCH[@]:1:3}"; do
    ((duration *= 60))
    ((duration += ${t#0} ))
  done
  while [ ${#us} -lt 6 ]; do us+=0; done
  ((us >= 500000)) && ((duration++))
  ((duration)) || ((duration++))
fi
echo -E Duration: "$duration"

-6

Wenn Sie eine GENAUE Dauer wünschen, vergessen Sie FFmpeg. Es gibt nur eine Schätzung basierend auf Dateigröße und durchschnittlicher Bitrate. Ich habe in einigen Fällen die geschätzte Freizeitdauer um 2x ermittelt!

Wenn unter Linux eine Datei nur während der Videoaufnahme erstellt und geändert wird, besteht eine alternative Lösung darin, die Erstellungsdauer und die Zeit der letzten Änderung zu verwenden, um die Dauer wie folgt zu berechnen:

stat -c "%X %Y" video.mpg | awk '{print $2 - $1}'

5
Wo haben Sie festgestellt, dass ffmpeg ungenau ist?
Aleb

4
% X ist der Zeitpunkt des letzten Zugriffs. % Y ist die Zeit seit der letzten Änderung. Dies sagt nichts über die Videolänge aus.
Joe Hillenbrand

1
Dies scheint ein Troll zu sein
George Chalhoub
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.