Android flac to wav

flac格式的音频属于“无损压缩”,对于我们最常说的“无损音频”来说,一般都是指传统CD格式中的16bit/44.1kHz采样率的文件格式,而知所以称为无损压缩,也是因为其包含了20Hz-22.05kHz这个完全覆盖人耳可闻范围的频响频率而得名。

简介

FLAC即是FreeLossless Audio Codec的缩写,全称应该叫OGGFLAC,中文可解为无损音频压缩编码。它是OGG计划的一部分,当然也就是开源、免费的了,这也难怪它这么快就得到了多家MP3厂商的支持。

FLAC是一套著名的自由音频压缩编码,其特点是无损压缩。FLAC压缩比可以达到2:1,对于无损压缩来说,这已经是相当高的比例了;而且它解码速度快,只需进行整数运算即可完成整个解码过程,对CPU的运算能力要求很低,所以普通的随身听,都可以轻松实现实时解码。

不同于其他有损压缩编码如MP3 及AAC,它不会破坏任何原有的音频资讯,所以可以还原音乐光盘音质。现在它已被很多软件及硬件音频产品所支持。简而言之,FLAC与MP3相仿,但是是无损压缩的,也就是说音频以FLAC方式压缩不会丢失任何信息。这种压缩与Zip的方式类似,但是FLAC将给你更大的压缩比率,因为

FLAC是专门针对音频的特点设计的压缩方式,并且你可以使用播放器播放FLAC压缩的文件,就象通常播放你的MP3文件一样。

补充:为无损格式,较ape而言,他体积大点,但是兼容性好,编码速度快,播放器支持更广

flac与mp3的区别

音质不同:flac不会破坏任何原有的音频信息,可以还原音乐光盘音质。mp3旨在大大减少音频数据量,利用mpeg音频第三层技术,将音乐压缩成1:10甚至1:12的小文件。压缩比不同:flac是一种专为pcm音频特性而设计的压缩模式,可以使用播放器直接播放FLAC压缩的文件。mp3其优点是压缩后占用空间小,适用于移动设备的存储和使用。

1、音质不同:flac不会破坏任何原有的音频信息,可以还原音乐光盘音质。mp3旨在大大减少音频数据量,利用mpeg音频第三层技术,将音乐压缩成1:10甚至1:12的小文件。

2、音频不同:flac音频以FLAC编码压缩后不会丢失任何信息,将FLAC文件还原为WAV文件后,与压缩前的WAV文件内容相同。mp3利用人耳对高频声音信号不敏感的特性,将时域波形信号转换成频域信号,并划分成多个频段,对不同的频段使用不同的压缩率,对高频加大压缩比对低频信号使用小压缩比,保证信号不失真。

3、压缩比不同:flac是一种专为pcm音频特性而设计的压缩模式,可以使用播放器直接播放FLAC压缩的文件。mp3其优点是压缩后占用空间小,适用于移动设备的存储和使用。

使用FLAC-library-Java库来实现 flac与wav互转。

1.flac to wav
import java.io.*;
import java.nio.charset.StandardCharsets;
import java.util.Arrays;
import java.util.zip.DataFormatException;public final class SimpleDecodeFlacToWav {public static void main(String[] args) throws IOException, DataFormatException {if (args.length != 2) {System.err.println("Usage: java SimpleDecodeFlacToWav InFile.flac OutFile.wav");System.exit(1);return;}try (BitInputStream in = new BitInputStream(new BufferedInputStream(new FileInputStream(args[0])));OutputStream out = new BufferedOutputStream(new FileOutputStream(args[1]))) {decodeFile(in, out);}}public static void decodeFile(BitInputStream in, OutputStream out) throws IOException, DataFormatException {// Handle FLAC header and metadata blocksif (in.readUint(32) != 0x664C6143)throw new DataFormatException("Invalid magic string");int sampleRate = -1;int numChannels = -1;int sampleDepth = -1;long numSamples = -1;for (boolean last = false; !last; ) {last = in.readUint(1) != 0;int type = in.readUint(7);int length = in.readUint(24);if (type == 0) {  // Stream info blockin.readUint(16);in.readUint(16);in.readUint(24);in.readUint(24);sampleRate = in.readUint(20);numChannels = in.readUint(3) + 1;sampleDepth = in.readUint(5) + 1;numSamples = (long)in.readUint(18) << 18 | in.readUint(18);for (int i = 0; i < 16; i++)in.readUint(8);} else {for (int i = 0; i < length; i++)in.readUint(8);}}if (sampleRate == -1)throw new DataFormatException("Stream info metadata block absent");if (sampleDepth % 8 != 0)throw new RuntimeException("Sample depth not supported");// Start writing WAV file headerslong sampleDataLen = numSamples * numChannels * (sampleDepth / 8);writeString("RIFF", out);writeLittleInt(4, (int)sampleDataLen + 36, out);writeString("WAVE", out);writeString("fmt ", out);writeLittleInt(4, 16, out);writeLittleInt(2, 0x0001, out);writeLittleInt(2, numChannels, out);writeLittleInt(4, sampleRate, out);writeLittleInt(4, sampleRate * numChannels * (sampleDepth / 8), out);writeLittleInt(2, numChannels * (sampleDepth / 8), out);writeLittleInt(2, sampleDepth, out);writeString("data", out);writeLittleInt(4, (int)sampleDataLen, out);// Decode FLAC audio frames and write raw sampleswhile (decodeFrame(in, numChannels, sampleDepth, out));}private static void writeLittleInt(int numBytes, int val, OutputStream out) throws IOException {for (int i = 0; i < numBytes; i++)out.write(val >>> (i * 8));}private static void writeString(String s, OutputStream out) throws IOException {out.write(s.getBytes(StandardCharsets.UTF_8));}private static boolean decodeFrame(BitInputStream in, int numChannels, int sampleDepth, OutputStream out)throws IOException, DataFormatException {// Read a ton of header fields, and ignore most of themint temp = in.readByte();if (temp == -1)return false;int sync = temp << 6 | in.readUint(6);if (sync != 0x3FFE)throw new DataFormatException("Sync code expected");in.readUint(1);in.readUint(1);int blockSizeCode = in.readUint(4);int sampleRateCode = in.readUint(4);int chanAsgn = in.readUint(4);in.readUint(3);in.readUint(1);temp = Integer.numberOfLeadingZeros(~(in.readUint(8) << 24)) - 1;for (int i = 0; i < temp; i++)in.readUint(8);int blockSize;if (blockSizeCode == 1)blockSize = 192;else if (2 <= blockSizeCode && blockSizeCode <= 5)blockSize = 576 << (blockSizeCode - 2);else if (blockSizeCode == 6)blockSize = in.readUint(8) + 1;else if (blockSizeCode == 7)blockSize = in.readUint(16) + 1;else if (8 <= blockSizeCode && blockSizeCode <= 15)blockSize = 256 << (blockSizeCode - 8);elsethrow new DataFormatException("Reserved block size");if (sampleRateCode == 12)in.readUint(8);else if (sampleRateCode == 13 || sampleRateCode == 14)in.readUint(16);in.readUint(8);// Decode each channel's subframe, then skip footerint[][] samples = new int[numChannels][blockSize];decodeSubframes(in, sampleDepth, chanAsgn, samples);in.alignToByte();in.readUint(16);// Write the decoded samplesfor (int i = 0; i < blockSize; i++) {for (int j = 0; j < numChannels; j++) {int val = samples[j][i];if (sampleDepth == 8)val += 128;writeLittleInt(sampleDepth / 8, val, out);}}return true;}private static void decodeSubframes(BitInputStream in, int sampleDepth, int chanAsgn, int[][] result)throws IOException, DataFormatException {int blockSize = result[0].length;long[][] subframes = new long[result.length][blockSize];if (0 <= chanAsgn && chanAsgn <= 7) {for (int ch = 0; ch < result.length; ch++)decodeSubframe(in, sampleDepth, subframes[ch]);} else if (8 <= chanAsgn && chanAsgn <= 10) {decodeSubframe(in, sampleDepth + (chanAsgn == 9 ? 1 : 0), subframes[0]);decodeSubframe(in, sampleDepth + (chanAsgn == 9 ? 0 : 1), subframes[1]);if (chanAsgn == 8) {for (int i = 0; i < blockSize; i++)subframes[1][i] = subframes[0][i] - subframes[1][i];} else if (chanAsgn == 9) {for (int i = 0; i < blockSize; i++)subframes[0][i] += subframes[1][i];} else if (chanAsgn == 10) {for (int i = 0; i < blockSize; i++) {long side = subframes[1][i];long right = subframes[0][i] - (side >> 1);subframes[1][i] = right;subframes[0][i] = right + side;}}} elsethrow new DataFormatException("Reserved channel assignment");for (int ch = 0; ch < result.length; ch++) {for (int i = 0; i < blockSize; i++)result[ch][i] = (int)subframes[ch][i];}}private static void decodeSubframe(BitInputStream in, int sampleDepth, long[] result)throws IOException, DataFormatException {in.readUint(1);int type = in.readUint(6);int shift = in.readUint(1);if (shift == 1) {while (in.readUint(1) == 0)shift++;}sampleDepth -= shift;if (type == 0)  // Constant codingArrays.fill(result, 0, result.length, in.readSignedInt(sampleDepth));else if (type == 1) {  // Verbatim codingfor (int i = 0; i < result.length; i++)result[i] = in.readSignedInt(sampleDepth);} else if (8 <= type && type <= 12)decodeFixedPredictionSubframe(in, type - 8, sampleDepth, result);else if (32 <= type && type <= 63)decodeLinearPredictiveCodingSubframe(in, type - 31, sampleDepth, result);elsethrow new DataFormatException("Reserved subframe type");for (int i = 0; i < result.length; i++)result[i] <<= shift;}private static void decodeFixedPredictionSubframe(BitInputStream in, int predOrder, int sampleDepth, long[] result)throws IOException, DataFormatException {for (int i = 0; i < predOrder; i++)result[i] = in.readSignedInt(sampleDepth);decodeResiduals(in, predOrder, result);restoreLinearPrediction(result, FIXED_PREDICTION_COEFFICIENTS[predOrder], 0);}private static final int[][] FIXED_PREDICTION_COEFFICIENTS = {{},{1},{2, -1},{3, -3, 1},{4, -6, 4, -1},};private static void decodeLinearPredictiveCodingSubframe(BitInputStream in, int lpcOrder, int sampleDepth, long[] result)throws IOException, DataFormatException {for (int i = 0; i < lpcOrder; i++)result[i] = in.readSignedInt(sampleDepth);int precision = in.readUint(4) + 1;int shift = in.readSignedInt(5);int[] coefs = new int[lpcOrder];for (int i = 0; i < coefs.length; i++)coefs[i] = in.readSignedInt(precision);decodeResiduals(in, lpcOrder, result);restoreLinearPrediction(result, coefs, shift);}private static void decodeResiduals(BitInputStream in, int warmup, long[] result) throws IOException, DataFormatException {int method = in.readUint(2);if (method >= 2)throw new DataFormatException("Reserved residual coding method");int paramBits = method == 0 ? 4 : 5;int escapeParam = method == 0 ? 0xF : 0x1F;int partitionOrder = in.readUint(4);int numPartitions = 1 << partitionOrder;if (result.length % numPartitions != 0)throw new DataFormatException("Block size not divisible by number of Rice partitions");int partitionSize = result.length / numPartitions;for (int i = 0; i < numPartitions; i++) {int start = i * partitionSize + (i == 0 ? warmup : 0);int end = (i + 1) * partitionSize;int param = in.readUint(paramBits);if (param < escapeParam) {for (int j = start; j < end; j++)result[j] = in.readRiceSignedInt(param);} else {int numBits = in.readUint(5);for (int j = start; j < end; j++)result[j] = in.readSignedInt(numBits);}}}private static void restoreLinearPrediction(long[] result, int[] coefs, int shift) {for (int i = coefs.length; i < result.length; i++) {long sum = 0;for (int j = 0; j < coefs.length; j++)sum += result[i - 1 - j] * coefs[j];result[i] += sum >> shift;}}}final class BitInputStream implements AutoCloseable {private InputStream in;private long bitBuffer;private int bitBufferLen;public BitInputStream(InputStream in) {this.in = in;}public void alignToByte() {bitBufferLen -= bitBufferLen % 8;}public int readByte() throws IOException {if (bitBufferLen >= 8)return readUint(8);elsereturn in.read();}public int readUint(int n) throws IOException {while (bitBufferLen < n) {int temp = in.read();if (temp == -1)throw new EOFException();bitBuffer = (bitBuffer << 8) | temp;bitBufferLen += 8;}bitBufferLen -= n;int result = (int)(bitBuffer >>> bitBufferLen);if (n < 32)result &= (1 << n) - 1;return result;}public int readSignedInt(int n) throws IOException {return (readUint(n) << (32 - n)) >> (32 - n);}public long readRiceSignedInt(int param) throws IOException {long val = 0;while (readUint(1) == 0)val++;val = (val << param) | readUint(param);return (val >>> 1) ^ -(val & 1);}public void close() throws IOException {in.close();}}
2. wav to flac
import java.io.*;
import java.nio.charset.StandardCharsets;
import java.util.zip.DataFormatException;public final class SimpleEncodeWavToFlac {public static void main(String[] args) throws IOException, DataFormatException {if (args.length != 2) {System.err.println("Usage: java SimpleEncodeWavToFlac InFile.wav OutFile.flac");System.exit(1);return;}try (InputStream in = new BufferedInputStream(new FileInputStream(args[0]));BitOutputStream out = new BitOutputStream(new BufferedOutputStream(new FileOutputStream(args[1])))) {encodeFile(in, out);}}public static void encodeFile(InputStream in, BitOutputStream out) throws IOException, DataFormatException {// Read and parse WAV file headersif (!readString(in, 4).equals("RIFF"))throw new DataFormatException("Invalid RIFF file header");readLittleInt(in, 4);if (!readString(in, 4).equals("WAVE"))throw new DataFormatException("Invalid WAV file header");if (!readString(in, 4).equals("fmt "))throw new DataFormatException("Unrecognized WAV file chunk");if (readLittleInt(in, 4) != 16)throw new DataFormatException("Unsupported WAV file type");if (readLittleInt(in, 2) != 0x0001)throw new DataFormatException("Unsupported WAV file codec");int numChannels = readLittleInt(in, 2);if (numChannels < 0 || numChannels > 8)throw new RuntimeException("Too many (or few) audio channels");int sampleRate = readLittleInt(in, 4);if (sampleRate <= 0 || sampleRate >= (1 << 20))throw new RuntimeException("Sample rate too large or invalid");readLittleInt(in, 4);readLittleInt(in, 2);int sampleDepth = readLittleInt(in, 2);if (sampleDepth == 0 || sampleDepth > 32 || sampleDepth % 8 != 0)throw new RuntimeException("Unsupported sample depth");if (!readString(in, 4).equals("data"))throw new DataFormatException("Unrecognized WAV file chunk");int sampleDataLen = readLittleInt(in, 4);if (sampleDataLen <= 0 || sampleDataLen % (numChannels * (sampleDepth / 8)) != 0)throw new DataFormatException("Invalid length of audio sample data");// Start writing FLAC file header and stream info metadata blockout.writeInt(32, 0x664C6143);out.writeInt(1, 1);out.writeInt(7, 0);out.writeInt(24, 34);out.writeInt(16, BLOCK_SIZE);out.writeInt(16, BLOCK_SIZE);out.writeInt(24, 0);out.writeInt(24, 0);out.writeInt(20, sampleRate);out.writeInt(3, numChannels - 1);out.writeInt(5, sampleDepth - 1);int numSamples = sampleDataLen / (numChannels * (sampleDepth / 8));out.writeInt(18, numSamples >>> 18);out.writeInt(18, numSamples >>>  0);for (int i = 0; i < 16; i++)out.writeInt(8, 0);// Read raw samples and encode FLAC audio framesfor (int i = 0; numSamples > 0; i++) {int blockSize = Math.min(numSamples, BLOCK_SIZE);encodeFrame(in, i, numChannels, sampleDepth, sampleRate, blockSize, out);numSamples -= blockSize;}}private static final int BLOCK_SIZE = 4096;private static String readString(InputStream in, int len) throws IOException {byte[] temp = new byte[len];for (int i = 0; i < temp.length; i++) {int b = in.read();if (b == -1)throw new EOFException();temp[i] = (byte)b;}return new String(temp, StandardCharsets.UTF_8);}private static int readLittleInt(InputStream in, int n) throws IOException {int result = 0;for (int i = 0; i < n; i++) {int b = in.read();if (b == -1)throw new EOFException();result |= b << (i * 8);}return result;}private static void encodeFrame(InputStream in, int frameIndex, int numChannels, int sampleDepth, int sampleRate, int blockSize, BitOutputStream out) throws IOException {int[][] samples = new int[numChannels][blockSize];int bytesPerSample = sampleDepth / 8;for (int i = 0; i < blockSize; i++) {for (int ch = 0; ch < numChannels; ch++) {int val = 0;for (int j = 0; j < bytesPerSample; j++) {int b = in.read();if (b == -1)throw new EOFException();val |= b << (j * 8);}if (sampleDepth == 8)samples[ch][i] = val - 128;elsesamples[ch][i] = (val << (32 - sampleDepth)) >> (32 - sampleDepth);}}out.resetCrcs();out.writeInt(14, 0x3FFE);out.writeInt(1, 0);out.writeInt(1, 0);out.writeInt(4, 7);out.writeInt(4, sampleRate % 10 == 0 ? 14 : 13);out.writeInt(4, numChannels - 1);switch (sampleDepth) {case  8:  out.writeInt(3, 1);  break;case 16:  out.writeInt(3, 4);  break;case 24:  out.writeInt(3, 6);  break;case 32:  out.writeInt(3, 0);  break;default:  throw new IllegalArgumentException();}out.writeInt(1, 0);out.writeInt(8, 0xFC | (frameIndex >>> 30));for (int i = 24; i >= 0; i -= 6)out.writeInt(8, 0x80 | ((frameIndex >>> i) & 0x3F));out.writeInt(16, blockSize - 1);out.writeInt(16, sampleRate / (sampleRate % 10 == 0 ? 10 : 1));out.writeInt(8, out.crc8);for (int[] chanSamples : samples)encodeSubframe(chanSamples, sampleDepth, out);out.alignToByte();out.writeInt(16, out.crc16);}private static void encodeSubframe(int[] samples, int sampleDepth, BitOutputStream out) throws IOException {out.writeInt(1, 0);out.writeInt(6, 1);  // Verbatim codingout.writeInt(1, 0);for (int x : samples)out.writeInt(sampleDepth, x);}}final class BitOutputStream implements AutoCloseable {private OutputStream out;private long bitBuffer;private int bitBufferLen;public int crc8;public int crc16;public BitOutputStream(OutputStream out) {this.out = out;bitBuffer = 0;bitBufferLen = 0;resetCrcs();}public void resetCrcs() {crc8 = 0;crc16 = 0;}public void alignToByte() throws IOException {writeInt((64 - bitBufferLen) % 8, 0);}public void writeInt(int n, int val) throws IOException {bitBuffer = (bitBuffer << n) | (val & ((1L << n) - 1));bitBufferLen += n;while (bitBufferLen >= 8) {bitBufferLen -= 8;int b = (int)(bitBuffer >>> bitBufferLen) & 0xFF;out.write(b);crc8 ^= b;crc16 ^= b << 8;for (int i = 0; i < 8; i++) {crc8 = (crc8 << 1) ^ ((crc8 >>> 7) * 0x107);crc16 = (crc16 << 1) ^ ((crc16 >>> 15) * 0x18005);}}}public void close() throws IOException {out.close();}}
3.wav 2 flac
import java.io.*;
import java.nio.charset.StandardCharsets;
import java.util.zip.DataFormatException;public final class DecodeFlacResidueToWav {public static void main(String[] args) throws IOException, DataFormatException {if (args.length != 2) {System.err.println("Usage: java DecodeFlacResidueToWav InFile.flac OutFile.wav");System.exit(1);return;}try (BitInputStream in = new BitInputStream(new BufferedInputStream(new FileInputStream(args[0])));OutputStream out = new BufferedOutputStream(new FileOutputStream(args[1]))) {decodeFile(in, out);}}public static void decodeFile(BitInputStream in, OutputStream out) throws IOException, DataFormatException {// Handle FLAC header and metadata blocksif (in.readUint(32) != 0x664C6143)throw new DataFormatException("Invalid magic string");int sampleRate = -1;int numChannels = -1;int sampleDepth = -1;long numSamples = -1;for (boolean last = false; !last; ) {last = in.readUint(1) != 0;int type = in.readUint(7);int length = in.readUint(24);if (type == 0) {  // Stream info blockin.readUint(16);in.readUint(16);in.readUint(24);in.readUint(24);sampleRate = in.readUint(20);numChannels = in.readUint(3) + 1;sampleDepth = in.readUint(5) + 1;numSamples = (long)in.readUint(18) << 18 | in.readUint(18);for (int i = 0; i < 16; i++)in.readUint(8);} else {for (int i = 0; i < length; i++)in.readUint(8);}}if (sampleRate == -1)throw new DataFormatException("Stream info metadata block absent");if (sampleDepth % 8 != 0)throw new RuntimeException("Sample depth not supported");// Start writing WAV file headerslong sampleDataLen = numSamples * numChannels * (sampleDepth / 8);writeString("RIFF", out);writeLittleInt(4, (int)sampleDataLen + 36, out);writeString("WAVE", out);writeString("fmt ", out);writeLittleInt(4, 16, out);writeLittleInt(2, 0x0001, out);writeLittleInt(2, numChannels, out);writeLittleInt(4, sampleRate, out);writeLittleInt(4, sampleRate * numChannels * (sampleDepth / 8), out);writeLittleInt(2, numChannels * (sampleDepth / 8), out);writeLittleInt(2, sampleDepth, out);writeString("data", out);writeLittleInt(4, (int)sampleDataLen, out);// Decode FLAC audio frames and write raw sampleswhile (decodeFrame(in, numChannels, sampleDepth, out));}private static void writeLittleInt(int numBytes, int val, OutputStream out) throws IOException {for (int i = 0; i < numBytes; i++)out.write(val >>> (i * 8));}private static void writeString(String s, OutputStream out) throws IOException {out.write(s.getBytes(StandardCharsets.UTF_8));}private static boolean decodeFrame(BitInputStream in, int numChannels, int sampleDepth, OutputStream out) throws IOException, DataFormatException {// Read a ton of header fields, and ignore most of themint temp = in.readByte();if (temp == -1)return false;int sync = temp << 6 | in.readUint(6);if (sync != 0x3FFE)throw new DataFormatException("Sync code expected");in.readUint(1);in.readUint(1);int blockSizeCode = in.readUint(4);int sampleRateCode = in.readUint(4);int chanAsgn = in.readUint(4);in.readUint(3);in.readUint(1);temp = Integer.numberOfLeadingZeros(~(in.readUint(8) << 24)) - 1;for (int i = 0; i < temp; i++)in.readUint(8);int blockSize;if (blockSizeCode == 1)blockSize = 192;else if (2 <= blockSizeCode && blockSizeCode <= 5)blockSize = 576 << (blockSizeCode - 2);else if (blockSizeCode == 6)blockSize = in.readUint(8) + 1;else if (blockSizeCode == 7)blockSize = in.readUint(16) + 1;else if (8 <= blockSizeCode && blockSizeCode <= 15)blockSize = 256 << (blockSizeCode - 8);elsethrow new DataFormatException("Reserved block size");if (sampleRateCode == 12)in.readUint(8);else if (sampleRateCode == 13 || sampleRateCode == 14)in.readUint(16);in.readUint(8);// Decode each channel's subframe, then skip footerint[][] samples = new int[numChannels][blockSize];decodeSubframes(in, sampleDepth, chanAsgn, samples);in.alignToByte();in.readUint(16);// Write the decoded samplesfor (int i = 0; i < blockSize; i++) {for (int j = 0; j < numChannels; j++) {int val = samples[j][i];if (sampleDepth == 8)val += 128;writeLittleInt(sampleDepth / 8, val, out);}}return true;}private static void decodeSubframes(BitInputStream in, int sampleDepth, int chanAsgn, int[][] result) throws IOException, DataFormatException {int blockSize = result[0].length;long[][] subframes = new long[result.length][blockSize];if (0 <= chanAsgn && chanAsgn <= 7) {for (int ch = 0; ch < result.length; ch++)decodeSubframe(in, sampleDepth, subframes[ch]);} else if (8 <= chanAsgn && chanAsgn <= 10) {decodeSubframe(in, sampleDepth + (chanAsgn == 9 ? 1 : 0), subframes[0]);decodeSubframe(in, sampleDepth + (chanAsgn == 9 ? 0 : 1), subframes[1]);} elsethrow new DataFormatException("Reserved channel assignment");for (int ch = 0; ch < result.length; ch++) {for (int i = 0; i < blockSize; i++)result[ch][i] = (int)subframes[ch][i];}}private static void decodeSubframe(BitInputStream in, int sampleDepth, long[] result) throws IOException, DataFormatException {in.readUint(1);int type = in.readUint(6);int shift = in.readUint(1);if (shift == 1) {while (in.readUint(1) == 0)shift++;}sampleDepth -= shift;if (type == 0)  // Constant codingin.readSignedInt(sampleDepth);else if (type == 1) {  // Verbatim codingfor (int i = 0; i < result.length; i++)in.readSignedInt(sampleDepth);} else if (8 <= type && type <= 12)decodeFixedPredictionSubframe(in, type - 8, sampleDepth, result);else if (32 <= type && type <= 63)decodeLinearPredictiveCodingSubframe(in, type - 31, sampleDepth, result);elsethrow new DataFormatException("Reserved subframe type");for (int i = 0; i < result.length; i++)result[i] <<= shift;}private static void decodeFixedPredictionSubframe(BitInputStream in, int predOrder, int sampleDepth, long[] result) throws IOException, DataFormatException {for (int i = 0; i < predOrder; i++)in.readSignedInt(sampleDepth);decodeResiduals(in, predOrder, result);}private static void decodeLinearPredictiveCodingSubframe(BitInputStream in, int lpcOrder, int sampleDepth, long[] result) throws IOException, DataFormatException {for (int i = 0; i < lpcOrder; i++)in.readSignedInt(sampleDepth);int precision = in.readUint(4) + 1;in.readSignedInt(5);for (int i = 0; i < lpcOrder; i++)in.readSignedInt(precision);decodeResiduals(in, lpcOrder, result);}private static void decodeResiduals(BitInputStream in, int warmup, long[] result) throws IOException, DataFormatException {int method = in.readUint(2);if (method >= 2)throw new DataFormatException("Reserved residual coding method");int paramBits = method == 0 ? 4 : 5;int escapeParam = method == 0 ? 0xF : 0x1F;int partitionOrder = in.readUint(4);int numPartitions = 1 << partitionOrder;if (result.length % numPartitions != 0)throw new DataFormatException("Block size not divisible by number of Rice partitions");int partitionSize = result.length / numPartitions;for (int i = 0; i < numPartitions; i++) {int start = i * partitionSize + (i == 0 ? warmup : 0);int end = (i + 1) * partitionSize;int param = in.readUint(paramBits);if (param < escapeParam) {for (int j = start; j < end; j++)result[j] = in.readRiceSignedInt(param);} else {int numBits = in.readUint(5);for (int j = start; j < end; j++)result[j] = in.readSignedInt(numBits);}}}}final class BitInputStream implements AutoCloseable {private InputStream in;private long bitBuffer;private int bitBufferLen;public BitInputStream(InputStream in) {this.in = in;}public void alignToByte() {bitBufferLen -= bitBufferLen % 8;}public int readByte() throws IOException {if (bitBufferLen >= 8)return readUint(8);elsereturn in.read();}public int readUint(int n) throws IOException {while (bitBufferLen < n) {int temp = in.read();if (temp == -1)throw new EOFException();bitBuffer = (bitBuffer << 8) | temp;bitBufferLen += 8;}bitBufferLen -= n;int result = (int)(bitBuffer >>> bitBufferLen);if (n < 32)result &= (1 << n) - 1;return result;}public int readSignedInt(int n) throws IOException {return (readUint(n) << (32 - n)) >> (32 - n);}public long readRiceSignedInt(int param) throws IOException {long val = 0;while (readUint(1) == 0)val++;val = (val << param) | readUint(param);return (val >>> 1) ^ -(val & 1);}public void close() throws IOException {in.close();}}
4.小结

wav2flac的过程结束后,flac文件的体积没啥变化,没有压缩。可以播放。

5.使用完整的jar包

wav2flac的过程结束后,flac文件的体积会变小。可以播放。详情参考githup库

6.资料

flac

flac convert

githup

Android flac to wav相关推荐

  1. flac转换成wav的方法,flac转wav步骤

    flac转换成wav的方法!如果你在工作中经常使用音频文件,那么肯定需要转换音频文件格式,音频文件的格式有很多种,多达二三十种,其中flac和wav就是重要的音频文件格式,这两种音频文件的质量都很高. ...

  2. 音频文件格式转换python实现——flac转wav

    在做语音相关工作时,经常会遇到要转换音频文件格式.读取音频格式有很多python库,比如librosa.scipy.io.wavfile.soundfile.pydub等等,但是笔者在实现flac转w ...

  3. flac 和 wav音频格式转换

    参考:https://stackoverflow.com/questions/23925494/how-to-convert-wav-to-flac-from-python wav to flac: ...

  4. linux 音频文件切割_linux下通过CUE分割APE、FLAC、WAV无损音频

    背景: 无损音乐的分享,大部分通过cue文件去播放一个很大的音频文件.这个在windows要去分割音频文件是意见很轻松的事情,在linux下面就要折腾点了,要在命令行下面进行处理,ape.flac.w ...

  5. foorbar关于flac和WAV文件的蛇皮走位(播放不了flac而可以用酷狗之类的播放)

    前言(吐槽) 写个foorbar关于flac和WAV文件的蛇皮走位的故事 本来打算上博客园开个小博客的,发现居然还要人工审核. 不等了,等到审核通过临时产生的想法都要忘了... 事情大概是这样纸滴 今 ...

  6. 如何使用Sidify Apple Music Converter for mac将 Apple Music 歌曲转换为 MP3、AAC、FLAC、WAV 或 AIFF?

    Sidify Apple Music Converter 是一款很不错的Apple Music 转 MP3 转换器.它将 Apple Music 快速转换为 MP3.AAC.FLAC.WAV 或 AI ...

  7. 将无损音乐flac,ape,wav格式导入ipod方法

    2019独角兽企业重金招聘Python工程师标准>>> 将无损音乐flac,ape,wav格式导入ipod方法 首先导入歌曲要有itunes软件 对于资料库的了解,是对于电脑上文件夹 ...

  8. Android 手机录制wav格式音频文件实现

    上一篇文章已经实现了在Android手机上使用MediaRecorder录音,但是后期在处理这些音频文件的时候发现3gp格式的音频不大方便处理,使用wav格式的音频处理起来更方便一些! 这里需要用到A ...

  9. ffmpeg批量转换flac为wav,m4a转换为wav,批量删除目录下某一后缀名文件,复制文件中有相同部分的文件

    m4a转换为wav建立python文件: def convert(save_path):files = glob.glob('%s/voxceleb2/*/*/*.m4a'%save_path)fil ...

最新文章

  1. 路由网关--spring cloud zuul
  2. 基于LNMP的简单电商网站架构
  3. 无电路板的微型电路制作
  4. android 消息循环机制--looper handler
  5. java本地监听zk服务器节点【动态上下线】
  6. 详解.NET IL代码(一)
  7. Qt工作笔记-双击TreeWidget列进行数据修改
  8. 仿新浪邮件输入自动提示jQuery插件
  9. linux下安装opencv4.4.0
  10. 真的已经讲烂了!java字符串转对象
  11. 用php绘制空心圆,html5使用canvas画空心圆与实心圆_html5教程技巧
  12. 短信开发的PDU格式
  13. 转 十道海量数据处理面试题与十个方法大总结
  14. NotImplementedError
  15. tcp/ip发送接收总体框架
  16. windows10 显示实时网速
  17. js运算符优先级问题
  18. Python求极限求积分,编程实现
  19. https://juejin.im/post/5ae081aaf265da0b767d263a
  20. Maximo 容器化改造试验

热门文章

  1. 修改QQ默认下载目录
  2. Jmeter基础系列4-创建一个HTTP请求实例
  3. Linux攻关之基础模块一 系统准备
  4. 出现无法访问的故障,ping出现请求超时time out,系目的主机网关造成问题排查过程
  5. SpringMVC @GetMapping注解路径冲突问题
  6. 多边形颜色填充-X扫描线算法
  7. java 获取当前时间所在自然周起止时间及自然周中的每一天
  8. 基于 Kubernetes 部署 Zookeeper,太有意思了!
  9. 双视图特征点匹配———使用RANSAC法剔除误差点
  10. JS 大杂烩(持续更新)