Come passare da .flac a .mp3 usando LAME e FLAC usando solo il Terminale?

27

Per molto tempo ho usato una tecnica relativamente grossa che coinvolge Audacity con un plugin LAME. Immagino, ma il fascino dell'approccio Terminal è che posso essere un po 'più fine con il mio [options] e forse usare file binari più aggiornati.

Inoltre, il mio MacBook sta invecchiando un po 'e se riesco a liberarmi di una GUI non necessaria, tanto meglio.

Grazie in anticipo.

    
posta boehj 24.02.2011 - 06:43
fonte

4 risposte

38

Conversione di un singolo file senza conservare i tag

brew install lame
flac --decode --stdout test.flac | lame --preset extreme - test.mp3

Uno script di shell che conserva alcuni tag ID3

#!/bin/bash

for f in "$@"; do
    [[ "$f" != *.flac ]] && continue
    album="$(metaflac --show-tag=album "$f" | sed 's/[^=]*=//')"
    artist="$(metaflac --show-tag=artist "$f" | sed 's/[^=]*=//')"
    date="$(metaflac --show-tag=date "$f" | sed 's/[^=]*=//')"
    title="$(metaflac --show-tag=title "$f" | sed 's/[^=]*=//')"
    year="$(metaflac --show-tag=date "$f" | sed 's/[^=]*=//')"
    genre="$(metaflac --show-tag=genre "$f" | sed 's/[^=]*=//')"
    tracknumber="$(metaflac --show-tag=tracknumber "$f" | sed 's/[^=]*=//')"

    flac --decode --stdout "$f" | lame --preset extreme --add-id3v2 --tt "$title" --ta "$artist" --tl "$album" --ty "$year" --tn "$tracknumber" --tg "$genre" - "${f%.flac}.mp3"
done

Per utilizzare lo script, salvalo da qualche parte come ~/bin/flac2mp3 e rendilo eseguibile con chmod +x ~/bin/flac2mp3 .

Questo converte tutti i file flac nella tua cartella Music:

find ~/Music/ -name '*.flac' -exec ~/bin/flac2mp3 {} \;

O leggermente più veloce, dal momento che chiama una sola volta flac2mp3:

find ~/Music/ -name '*.flac' -print0 | xargs -0 ~/bin/flac2mp3
    
risposta data 24.02.2011 - 10:51
fonte
10

ffmpeg conserverebbe i tag (ma non quelli di copertina) per impostazione predefinita.

for f in *.flac; do ffmpeg -i "$f" -aq 1 "${f%flac}mp3"; done

-aq 1 corrisponde a -V 1 in lame. -acodec libfaac converte i file in AAC:

for f in *.flac; do ffmpeg -i "$f" -acodec libfaac -aq 200 "${f%flac}m4a"; done
    
risposta data 28.01.2013 - 11:57
fonte
3

ho preso ciò che avevi, ma poi l'ho fatto funzionare ancora più velocemente usando xargs per parallelizzare i lavori.

find <directory> -name '*.flac' -print0 | xargs -0 -P8 -n1  /usr/local/bin/flac2mp3

Quindi questo è lo script di cui sopra     / usr / local / bin / flac2mp3

#!/usr/bin/env bash

for f in "$@"; do
  [[ "$f" != *.flac ]] && continue
  album="$(metaflac --show-tag=album "$f" | sed 's/[^=]*=//')"
  artist="$(metaflac --show-tag=artist "$f" | sed 's/[^=]*=//')"
  date="$(metaflac --show-tag=date "$f" | sed 's/[^=]*=//')"
  title="$(metaflac --show-tag=title "$f" | sed 's/[^=]*=//')"
  year="$(metaflac --show-tag=date "$f" | sed 's/[^=]*=//')"
  genre="$(metaflac --show-tag=genre "$f" | sed 's/[^=]*=//')"
  tracknumber="$(metaflac --show-tag=tracknumber "$f" | sed 's/[^=]*=//')"

  flac --decode --stdout "$f" \ 
         | lame --preset extreme \
                --add-id3v2 \
                 --tt "$title" \
                 --ta "$artist" \
                 --tl "$album" \
                 --ty "$year" \
                 --tn "$tracknumber" \
                 --tg "$genre" \
                 - "${f%.flac}.mp3"
done

e ecco alcune statistiche per l'aumento delle prestazioni usando il parallelismo.

find <dirOfFlac24s> -name '*.flac -print0 | xargs -0 -P8 -n1 /usr/local/bin/flac2mp320  

0.00s user 0.00s system 60% cpu 0.002 total
115.94s user 1.40s system 359% cpu 32.655 total

time /usr/local/bin/flac2mp320 <dirOfFlac24s>/*.flac
96.63s user 1.46s system 109% cpu 1:29.98 total

puoi vedere che utilizza anche le mie CPU in modo più efficace, ho un Intel i7, quindi 8 è probabilmente il giusto numero di processi.

    
risposta data 29.07.2017 - 21:10
fonte
2

Trovato questo thread durante il tentativo di eseguire la codifica diretta di MP3 dai file di origine FLAC. La risposta di Boehj offre un'opzione di scripting decente, ma personalmente preferisco usare FFmpeg, quindi questo è lo script di Bash che ho ricevuto con per gestire questo compito. Testato e funziona alla grande in macOS Sierra (10.12.2).

Perquisiti: dovresti avere ffmpeg e lame già installati sul tuo Mac. Il modo più semplice per farlo è tramite Homebrew. Prima assicurati di avere installato Homebrew in questo modo:

/usr/bin/ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"

Quindi esegui questo comando per installare ffmpeg e lame :

brew install ffmpeg lame

Una volta fatto, sei pronto per eseguire questo script. Questo script cercherà i file FLAC nella directory path/to/FLAC/files ma può essere modificato in . se i file FLAC si trovano nella stessa directory in cui viene eseguito questo script. Quando viene eseguito creerà un mp3/ sottodirectory in cui saranno collocati tutti i file MP3.

find -E "path/to/FLAC/files" -type f -iregex ".*\.(FLAC)$" |\
  while read full_audio_filepath
  do

    # Break up the full audio filepath stuff into different directory and filename components.
    audio_dirname=$(dirname "${full_audio_filepath}");
    audio_basename=$(basename "${full_audio_filepath}");
    audio_filename="${audio_basename%.*}";
    # audio_extension="${audio_basename##*.}";

    # Set the MP3
    mp3_dirpath="${audio_dirname}/mp3";
    mp3_filepath="${mp3_dirpath}/${audio_filename}.mp3";

    # Create the child MP3 directory.
    mkdir -p "${mp3_dirpath}";

    # Get the track metadata.
    mp3_title=$(ffprobe 2> /dev/null -show_format "${full_audio_filepath}" | grep -i TAG:TITLE= | cut -d '=' -f 2- );
    mp3_artist=$(ffprobe 2> /dev/null -show_format "${full_audio_filepath}" | grep -i TAG:ARTIST= | cut -d '=' -f 2- );
    mp3_album=$(ffprobe 2> /dev/null -show_format "${full_audio_filepath}" | grep -i TAG:ALBUM= | cut -d '=' -f 2- );
    mp3_year=$(ffprobe 2> /dev/null -show_format "${full_audio_filepath}" | grep -i TAG:YEAR= | cut -d '=' -f 2- );
    mp3_track=$(ffprobe 2> /dev/null -show_format "${full_audio_filepath}" | grep -i TAG:TRACK= | cut -d '=' -f 2- | sed 's/^0*//' );
    mp3_tracktotal=$(ffprobe 2> /dev/null -show_format "${full_audio_filepath}" | grep -i TAG:TRACKTOTAL= | cut -d '=' -f 2- | sed 's/^0*//' );
    mp3_genre=$(ffprobe 2> /dev/null -show_format "${full_audio_filepath}" | grep -i TAG:GENRE= | cut -d '=' -f 2- );

    # Where the magic happens.
    ffmpeg -y -v quiet -nostdin -i "${full_audio_filepath}" -ar 44100 -sample_fmt s16 -ac 2 -f s16le -acodec pcm_s16le - | \
      lame --quiet --add-id3v2 --pad-id3v2 --tt "${mp3_title}" --ta "${mp3_artist}" --tl "${mp3_album}" --tn "${mp3_track}"/"${mp3_tracktotal}" --tg "${mp3_genre}" -r -m s --lowpass 19.7 -V 3 --vbr-new -q 0 -b 96 --scale 0.99 --athaa-sensitivity 1 - "${mp3_filepath}";

  done

Alcune note su cose che ho imparato "The Hard Way ™" così altri possono ottenere da ciò che ho fatto in modo diverso in questo script rispetto ad altri su Internet.

  • I comandi grep per l'analisi dei tag (utilizzando FFprobe che è installato con FFmpeg) fanno distinzione tra maiuscole e minuscole utilizzando -i opzione per renderlo grep -i .
  • Il seguente comando cut ora è limitato alla divisione dell'output solo in base al primo = in un nome di tag con l'opzione -f 2- che rende il comando cut -d '=' -f 2- . Ad esempio, Pavement ha una canzone intitolata "5-4 = Unity" e se solo la seconda parte sono stati selezionati tramite taglio che il titolo sarebbe stato troncato su "5-4".
  • Per i numeri di traccia track e totali ho aggiunto un pipe extra a sed che elimina gli zeri iniziali: sed 's/^0*//' .
  • In script simili su Internet, l'output di FFmpeg è qualcosa come -f wav e in pratica comprime l'output FFmpeg che non ha senso in un'installazione di pipe dove LAME sta per ricodificarlo. Invece l'output qui è impostato su -f s16le -acodec pcm_s16le che è fondamentalmente l'output RAW; perfetto per convogliare l'audio in un altro processo come questo.
  • Per gestire l'output RAW sul lato LAME della pipe, ho dovuto aggiungere l'opzione -r .
  • Nota anche le opzioni --tt , --ta , --tl , --tn e --tg ID3v2 per LAME. Quando l'audio viene trasmesso in streaming / inviato da un processo a LAME, i metadati del file di origine vengono persi. Un'opzione suggerita è di ottenere FFmpeg per salvare i metadati in un file di testo impostando l'opzione con -f ffmetadata "[metadata filename here]" e quindi eseguendo nuovamente FFmpeg con qualcosa del genere: -i "[metadata filename here]" -map_metadata 1 -c:a copy [destination mp3 file] id3v2_version 3 -write_id3v1 1 . Funziona, ma nota il requisito per un file di destinazione. Sembra che FFmpeg importi solo i metadati quando può copiare il file che sembra un processo molto dispendioso. Usando FFprobe per ottenere valori e quindi impostandoli in LAME con --tt , --ta , --tl , --tn e --tg le opzioni funzionano meglio; tutti i metadati sono scritti in posizione, quindi è necessario generare un file duplicato.
risposta data 02.01.2017 - 04:33
fonte

Leggi altre domande sui tag