2
@echo off
rem ffmpeg -i test.ts 2>&1 | find "Duration" > duration.txt
rem set /p duration=<duration.txt

set duration=  Duration: 01:09:52.59, start: 0.136811, bitrate: 10740 kb/s

set /a Hours=%duration:~12,2%
set /a Mins=%duration:~15,2%
set /a Secs=%duration:~18,2%

set /a Duration_In_Seconds=(hours*3600)+(mins*60)+secs

echo %duration_In_seconds%

minsという整数変数に「09」をセットしようとすると失敗します。

無効な番号。数値定数は、10 進数 (17)、16 進数 (0x11)、または 8 進数 (021) のいずれかです。

文字列を整数に変換する必要があるので、基本的な数学を使用して期間を秒単位で計算できます

4

2 に答える 2

2

SET のヘルプ (HELP SETコマンド プロンプトから入力) を読むと、SET が常に 0 のプレフィックス付きの数字を 8 進数として解釈することがわかります。基数 10 を強制する設定はありません。代わりに、ゼロで始まらないように文字列を操作する必要があります。

一時ファイルに書き込む必要はありません。FOR /F を使用して出力を解析できます。また、出力を時、分、および秒のトークンに分割することもできます。

先頭の 0 を回避する 2 つの簡単な方法を知っています。

1 つの方法は、値の前に 1 を付けてから、mod (剰余) 演算子を使用して目的の数値を抽出することです。あなたの場合、時間は 99 の最大値に制限されます。最大 999 をサポートする必要がある場合は、10 を前に付けて 1000 の mod を取ることができます。単一の SET / で複数の割り当てを実行できることに注意してください。を使用し,て各割り当てを区切るステートメント。SET /A は正しい優先順位に従うため、括弧は必要ありません。

@echo off
for /f "tokens=2-4 delims=:. " %%A in ('ffmpeg -i test.ts 2^>^&1 ^| find "Duration"') do (
  set /a Hours=1%%A%%100, Mins=1%%B%%100, Secs=1%%C%%100, Duration_In_Seconds=Hours*3600+Mins*60+Secs
)

もう 1 つの方法は、FOR /F ループを使用して先頭のゼロを削除することです。1 を追加してから 10 で割り、ゼロのみの文字列が処理されるようにします。

@echo off
for /f "tokens=2-4 delims=:. " %%A in ('ffmpeg -i test.ts 2^>^&1 ^| find "Duration"') do (
  for /f "delims=0" %%N in ("%%A1") do set /a Hours=%%N/10
  for /f "delims=0" %%N in ("%%B1") do set /a Mins=%%N/10
  for /f "delims=0" %%N in ("%%C1") do set /a Secs=%%N/10
  set /a Duration_In_Seconds=Hours*3600+Mins*60+Secs
)

必要に応じて、小数秒が 0.5 以上の場合に秒を切り上げるようにコードを拡張するのは簡単です。余分なトークンを解析する区切り文字として を追加するだけ,で、丸めを行うための数学のトリックがいくつか実行されます。

@echo off
for /f "tokens=2-5 delims=:., " %%A in ('ffmpeg -i test.ts 2^>^&1 ^| find "Duration"') do (
  for /f "delims=0" %%N in ("%%A1") do set /a Hours=%%N/10
  for /f "delims=0" %%N in ("%%B1") do set /a Mins=%%N/10
  for /f "delims=0" %%N in ("%%C%%D1") do set /a Secs=(%%N+500)/1000
  set /a Duration_In_Seconds=Hours*3600+Mins*60+Secs
)
于 2012-11-01T11:19:30.300 に答える
0

16 進数から 10 進数への変換を使用すると、次のコードは範囲 [0..39999] 内の数値に対して機能します。

set str=000039999
set /a dgt=0x!str!
set /a "dgt=(10000*(dgt&983040)>>16)+(1000*(dgt&61440)>>12)+(100*(dgt&3840)>>8)+(10*(dgt&240)>>4)+(dgt&15)"
echo str="!str!"
echo dgt="!dgt!"
于 2020-03-20T09:42:54.420 に答える