1

現在、プロジェクトで Phonegap を使用しており、何千もの画像をダウンロードする必要があります。今では、Phonegap の API を使用して Javascript で直接実行されていました。ただし、処理にかなりの時間がかかります (5 ~ 10 分)。

次に、このタスクをピュア Java で行うことにしました。それはうまくいきます!でも、もっと速くできると思います。

~1k の画像をダウンロードした後、アプリは 4 ~ 5 秒ごとに「GC_CONCURRENT FREED」をスローし始め、1 ~ 2 秒間ダウンロードを完全に停止します。Eclipse のネットワーク統計はジェットコースターのように機能します。

ここにあなたが待っているものがあります:

私のダウンロードクラス:

public class DownloadImage extends AsyncTask<String, Integer, Boolean>
{   
    protected static String destination = Environment.getExternalStorageDirectory().getAbsolutePath() + "/Android/data/com.test.test/cache/pic_test/";
    protected static Context context;
    protected static String taskName;
    protected static ArrayList<String> urls;
    protected static int totalSize;

    public DownloadImage(Context context, String taskName, ArrayList<String> urls) {
        DownloadImage.context = context;
        DownloadImage.taskName = taskName;
        DownloadImage.urls = urls;
        DownloadImage.totalSize = urls.size();
    }

    public DownloadImage() {}

    @Override
    protected Boolean doInBackground(String... params) {
        String urlstring, filename;
        URL url;
        HttpURLConnection urlConnection;
        File tmpFile;
        FileOutputStream fileOutput;
        InputStream inputStream;
        byte[] buffer = new byte[8192];
        int bufferLength;

        try {
            while(DownloadImage.urls.size() > 0) {
                try {
                    urlstring = DownloadImage.urls.remove(0);
                    url = new URL(urlstring);
                    filename = urlstring.substring(urlstring.lastIndexOf("/")+1, urlstring.length());
                    urlConnection = (HttpURLConnection) url.openConnection();

                    //configuration de la connexion
                    urlConnection.setRequestMethod("GET");
                    urlConnection.setDoOutput(true);
                    urlConnection.setConnectTimeout(5000);
                    urlConnection.setReadTimeout(5000);
                    urlConnection.connect();

                    tmpFile = new File(DownloadImage.destination+filename + ".temp");
                    fileOutput = new FileOutputStream(tmpFile);
                    inputStream = urlConnection.getInputStream();

                    bufferLength = 0;
                    //lecture du flux
                    Log.d("DownloadFile","Téléchargement en cours "+filename);
                    while ( (bufferLength = inputStream.read(buffer)) > 0 ) {
                        fileOutput.write(buffer, 0, bufferLength);
                    }
                    fileOutput.close();
                    inputStream.close();
                    ((TestActivity)(DownloadImage.context)).sendJavascript("Application.testCallback('"+DownloadImage.totalSize+"', '"+(DownloadImage.totalSize - DownloadImage.urls.size() + 1)+"')");
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        } catch(IndexOutOfBoundsException e) {}
        return false;
    }

    @Override
    protected void onPostExecute(Boolean result) {
        if(DownloadImage.context instanceof TestActivity) {
            Log.d("test_flo", "no task left in queue");
            //((TestActivity) this.context).finishTask(this.taskName);
        }
    }
}

私の主な活動:

private class AndroidFunction {
    @SuppressWarnings("unused")
    private WebView mAppView;
    @SuppressWarnings("unused")
    private DroidGap mGap;

    public AndroidFunction(DroidGap gap, WebView view) {
        mGap = gap;
        mAppView = view;
    }

    @SuppressWarnings("unused")
    public String test() {          
        ArrayList<String> urls = new ArrayList<String>();
        try {
            BufferedReader br = new BufferedReader(new InputStreamReader(getAssets().open("testpic.txt")));
            String line;
            while ((line = br.readLine()) != null) {
                urls.add(line);
            }
            br.close();
        } catch(Exception e) {}
        new DownloadImage(TestActivity.this, "test", urls).execute();
        new DownloadImage().execute();
        new DownloadImage().execute();
        new DownloadImage().execute();
        new DownloadImage().execute();
        return "";
    }
}

ご覧のとおり、各ループ間でオブジェクトを再利用して、できるだけ少ないオブジェクトを消費しようとしました。これらの「GC_CONCURRENT FREED」をまだスローしている理由がわかりますか?

ご回答ありがとうございます。

4

0 に答える 0