java提高线程和SwingWorker绘制FFT图表的性能
我正在使用Java开发一个概念验证应用程序。我注意到,与运行CSharp的版本相比,我的Java应用程序速度较慢。我想要一个概念或建议来提高性能
我用一个线程从麦克风捕捉声音,在这个线程中,我有另一个线程:
- 要在硬盘上保存声音字节
- 另一种方法是在时间和FFT(快速傅立叶变换)中绘制字节(样本)李>
不幸的是,代码很长,SSCCE(很难提取功能代码,以便发布短代码)
我的代码是在Git中发布的,为了显示它的性能,我做了一个video
- 我想知道light Java库(图表类型),它可以绘制或绘制我的时间和FFT每秒变化很多次强>
我需要一些建议来发现这段代码逻辑中的缺陷强>
final AudioFormat audioformat = new AudioFormat(16000 /*Frequency*/, 16 /* two bytes per sample */, 2 /*Stereo*/, true /*Signed*/, true /*bigEndian*/); final DataLine.Info dlInfo = new DataLine.Info(TargetDataLine.class, audioformat); if (!AudioSystem.isLineSupported(dlInfo)) { System.out.println("Line not supported"); } try { final TargetDataLine tdLine = (TargetDataLine) AudioSystem.getLine(dlInfo); if (jtbCapture.isSelected()) { fileRecordedWav = new File("Some/Path/Filename.wav"); final AudioFileFormat.Type afType = AudioFileFormat.Type.WAVE; thrdRecording = new Thread() { @Override public void run() { try { tdLine.open(audioformat); int bufferSize = (int) audioformat.getSampleRate() * audioformat.getFrameSize(); //1Sec/40 = 25 milli Second System.out.println("bufferSize:" + bufferSize); //INI Save File final PipedOutputStream SrcSavePOStream = new PipedOutputStream(); final PipedInputStream SnkSavePIStream = new PipedInputStream(); SnkSavePIStream.connect(SrcSavePOStream); aisRecording = new AudioInputStream((InputStream)SnkSavePIStream, audioformat, AudioSystem.NOT_SPECIFIED); Runnable runnableSave = () -> { try { AudioSystem.write(aisRecording, afType, fileRecordedWav); } catch (IOException ex) { /*Pipe broken*/} }; Thread threadSave = new Thread(runnableSave); threadSave.start(); //END Save File // INI Graph File final PipedOutputStream SrcPlotPOStream = new PipedOutputStream(); final PipedInputStream SnkPlotPIStream = new PipedInputStream(); SnkPlotPIStream.connect(SrcPlotPOStream); Runnable runnablePlot = () -> { try { int qtyBytes; byte[] incomingBytes = new byte[bufferSize]; int numBytesPerSample = audioformat.getSampleSizeInBits()/8; int numChannels = audioformat.getChannels(); int frameSize = audioformat.getFrameSize(); int bytesframeSize = numBytesPerSample*numChannels; Double sampleRateTime = (double)audioformat.getSampleRate(); while ((qtyBytes = SnkPlotPIStream.read(incomingBytes)) != -1) { byte[] bytesSamples = new byte[qtyBytes]; System.arraycopy(incomingBytes, 0, bytesSamples, 0, qtyBytes); int qtySamples = qtyBytes/frameSize; double[] samplesTime = getSamplesBuffer(bytesSamples, numBytesPerSample, numChannels, "left", 0, qtySamples); double pow = Math.floor(Math.log(qtySamples) / Math.log(2.0)); int sizePower2 = (int)Math.pow(2.0, pow); double[] freqs = new double[qtySamples]; double[] samplesPower2 = new double[sizePower2]; System.arraycopy(samplesTime, 0, samplesPower2, 0, sizePower2); double[] time = new double[qtySamples]; double counter = 0.0; for (int i = 0; i < time.length; i++) { time[i] = counter / sampleRateTime;// counter++; freqs[i] = (double)i/qtySamples*sampleRateTime/1000.0; } // INI Time SwingWorker swingWorkerPlotTime = new SwingWorker() { PanelChart panelChartTimeSound = new PanelChart(); @Override protected Void doInBackground() throws Exception { panelChartTimeSound.addVble("sound", time, samplesTime, Color.GREEN); return null; } @Override protected void done() { if (panelChartTimeSound.hasPlottable()) { setPanelInPanel(jpMakeSoundTime, panelChartTimeSound.getChart(jpMakeSoundTime.getWidth(), jpMakeSoundTime.getHeight())); panelChartTimeSound.delAllVble(); panelChartTimeSound = null; } } }; swingWorkerPlotTime.execute(); // END Time // INI FFT double[] fft = FourierTransform.customFFT(samplesPower2); double[] halfFFT = new double[sizePower2/2]; double[] halfFreq = new double[sizePower2/2]; System.arraycopy(freqs, 0, halfFreq, 0, halfFreq.length); System.arraycopy(fft, 0, halfFFT, 0, halfFFT.length); SwingWorker swingWorkerPlotFreq = new SwingWorker() { PanelChart panelChartFreqSound = new PanelChart(); @Override protected Void doInBackground() throws Exception { panelChartFreqSound.addVble("sound", halfFreq, halfFFT, new Color(0, 255, 192)); return null; } @Override protected void done() { if (panelChartFreqSound.hasPlottable()) { setPanelInPanel(jpMakeSoundFFT, panelChartFreqSound.getChart(jpMakeSoundFFT.getWidth(), jpMakeSoundFFT.getHeight())); panelChartFreqSound.delAllVble(); panelChartFreqSound = null; } } }; swingWorkerPlotFreq.execute(); // END FFT } } catch (IOException ex) { System.out.println("runnablePlot:" + ex.toString()); } }; Thread threadPlot = new Thread(runnablePlot); threadPlot.start(); // END Graph File // INI Microphone Capture byte[] buffer = new byte[bufferSize]; tdLine.start(); while (true) { int count = tdLine.read(buffer, 0, buffer.length); if (count > 0) { SrcSavePOStream.write(buffer); SrcPlotPOStream.write(buffer); } } // END Microphone Capture } catch (LineUnavailableException | IOException ex) { System.out.println("thrdRecording.run:" + ex.toString()); } } }; thrdRecording.start(); }
共 (0) 个答案