簡體   English   中英

內存泄漏和優化

[英]Leak of memory and optimization

我目前正在開發一個Android應用程序,由於“ Out of Memory”(內存不足)之類的問題,我無法結束它,我認為代碼中有兩部分可能會導致泄漏。

  • 首先:該應用程序必須同時播放12種音調(10個不同的頻率)。 我在Stack Overflow上找到了一段代碼,該代碼可以讓我同時播放頻率列表:(我認為這是AudioTrack引起的,但我不知道如何解決)

     public static void runList(final List<Double> freq) { if(audioTrack!=null){ audioTrack.release(); audioTrack=null; } final List<AudioTrack> audioTrackList = new ArrayList(); final AudioTrack audioTrack0; final AudioTrack audioTrack1; genTone(freq.get(0)); audioTrack0 = new AudioTrack(AudioManager.STREAM_MUSIC, (int) sampleRate, AudioFormat.CHANNEL_OUT_DEFAULT,AudioFormat.ENCODING_PCM_16BIT, generatedSnd.length, AudioTrack.MODE_STREAM); audioTrack0.play(); audioTrack0.write(generatedSnd, 0, generatedSnd.length); genTone(freq.get(1)); audioTrack1 = new AudioTrack(AudioManager.STREAM_MUSIC, (int) sampleRate, AudioFormat.CHANNEL_OUT_DEFAULT,AudioFormat.ENCODING_PCM_16BIT, generatedSnd.length, AudioTrack.MODE_STREAM); audioTrack1.play(); audioTrack1.write(generatedSnd, 0, generatedSnd.length); handler.postDelayed(new Runnable() { @Override public void run() { //compteur : not more than 2 AudioTrack audioTrack0.release(); audioTrack1.release(); } }, 1000); } 

(與此同時,我只能同時播放2個音調)

  • 然后:在同一活動中,應用程序必須在屏幕上顯示10張圖像視圖,每個圖像都以不同的方式移動。 所有這些圖像視圖以前都是從位圖解碼的。 我認為泄漏來自這里。 我嘗試使用位圖后將其釋放,但無濟於事,在崩潰(內存不足)之前,我只能在屏幕上顯示3或4張圖像。 也許有一種更好,更輕松的方法來為圖像設置動畫,例如,為圖像設置動畫並使其遵循三角形的方式,我使用以下方法:

     private void triangleAnim(final ImageView patternImage, final int bpm, final int i, final double frequency) { resetN(); int randomLeft = (int)(Math.random() * (maxRandomLeft-minRandomLeft)) + minRandomLeft; int randomTop = (int)(Math.random() * (maxRandomTop-minRandomTop)) + minRandomTop; final Animation anim = new TranslateAnimation(randomLeft, randomLeft + 300,randomTop,randomTop + 300 ); anim.setDuration(60000/bpm); final Animation anim2 = new TranslateAnimation(randomLeft +300, randomLeft-300, randomTop+300, randomTop+300 ); anim2.setDuration(60000/bpm); final Animation anim3 = new TranslateAnimation(randomLeft-300, randomLeft, randomTop+300, randomTop ); anim3.setDuration(60000/bpm); su = new SoundUtils(); su.setDuration(60000/bpm); patternImage.startAnimation(anim); anim.setAnimationListener(new Animation.AnimationListener() { @Override public void onAnimationEnd(Animation animation) { patternImage.startAnimation(anim2); ; } @Override public void onAnimationRepeat(Animation animation) { } @Override public void onAnimationStart(Animation animation) { // TODO Auto-generated method stub } }); anim2.setAnimationListener(new Animation.AnimationListener() { @Override public void onAnimationEnd(Animation animation) { patternImage.startAnimation(anim3); ; incrementN(); } @Override public void onAnimationRepeat(Animation animation) { } @Override public void onAnimationStart(Animation animation) { // TODO Auto-generated method stub } }); anim3.setAnimationListener(new Animation.AnimationListener() { @Override public void onAnimationEnd(Animation animation) { if(n <= i){ patternImage.startAnimation(anim); } } @Override public void onAnimationRepeat(Animation animation) { } @Override public void onAnimationStart(Animation animation) { // TODO Auto-generated method stub } }); } 
  • 最后,是否有任何軟件或代碼或其他任何可以幫助我查找應用程序內存泄漏的地方? 如果需要,我可以從LogCat鏈接您的錯誤。

對不起,我的英文,希望沒有太多的錯誤。

更新:

這是我的日志:

07-31 17:54:03.931: E/AndroidRuntime(15181): java.lang.OutOfMemoryError
07-31 17:54:03.931: E/AndroidRuntime(15181):    at      android.graphics.Bitmap.nativeCreate(Native Method)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.graphics.Bitmap.createBitmap(Bitmap.java:903)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.graphics.Bitmap.createBitmap(Bitmap.java:880)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.graphics.Bitmap.createBitmap(Bitmap.java:847)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.CameraBridgeViewBase.AllocateCache(CameraBridgeViewBase.java:451)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.JavaCameraView.initializeCamera(JavaCameraView.java:184)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.JavaCameraView.connectCamera(JavaCameraView.java:239)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.CameraBridgeViewBase.onEnterStartedState(CameraBridgeViewBase.java:355)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.CameraBridgeViewBase.processEnterState(CameraBridgeViewBase.java:318)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.CameraBridgeViewBase.checkCurrentState(CameraBridgeViewBase.java:311)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.CameraBridgeViewBase.enableView(CameraBridgeViewBase.java:228)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at ui.fragment.TakePictureFragment$1.onManagerConnected(TakePictureFragment.java:71)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at org.opencv.android.AsyncServiceHelper$1.onServiceConnected(AsyncServiceHelper.java:318)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.app.LoadedApk$ServiceDispatcher.doConnected(LoadedApk.java:1119)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.app.LoadedApk$ServiceDispatcher$RunConnection.run(LoadedApk.java:1136)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.os.Handler.handleCallback(Handler.java:733)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.os.Handler.dispatchMessage(Handler.java:95)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.os.Looper.loop(Looper.java:157)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at android.app.ActivityThread.main(ActivityThread.java:5356)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at java.lang.reflect.Method.invokeNative(Native Method)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at java.lang.reflect.Method.invoke(Method.java:515)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
07-31 17:54:03.931: E/AndroidRuntime(15181):    at dalvik.system.NativeStart.main(Native Method)

要解碼位圖,我可以這樣:

private Bitmap decodeFile(File f){
    try {
        //decode image size
        BitmapFactory.Options o = new BitmapFactory.Options();
        o.inJustDecodeBounds = true;
        BitmapFactory.decodeStream(new FileInputStream(f),null,o);              
        //Find the correct scale value. It should be the power of 2.
        final int REQUIRED_SIZE=70;
        int width_tmp=o.outWidth, height_tmp=o.outHeight;
        int scale=1;
        while(true){
            if(width_tmp/2<REQUIRED_SIZE || height_tmp/2<REQUIRED_SIZE)
                break;
            width_tmp/=2;
            height_tmp/=2;
            scale++;
        }

        //decode with inSampleSize
        BitmapFactory.Options o2 = new BitmapFactory.Options();
        o2.inSampleSize=scale;
        return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
    } catch (FileNotFoundException e) {}
    return null;

}

只是想一想:確保關閉您的InputStream, BitmapFactory.decodeStream(); 在源代碼中似乎沒有這樣做

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM