为什么达到一定数量后进度会下降?

时间:2019-02-08 11:42:42

标签: java android firebase

我正在从Firebase Firestore下载文件,其中包含文件的URL。文件大小超过100 MB。我正在使用Asyctask执行代码,但是一旦达到一定值,它就会减少。

我尝试获取进度的绝对值,但仍然会降低。

public static final class DownloadGameTask extends AsyncTask<String, Integer, String> {
    private Context mContext;

    DownloadGameTask(Context context) {
        mContext = context;
    }

    @Override
    protected void onPreExecute() {
        super.onPreExecute();

        //Kaylangan ng ID for Oreo above
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            //Kapag oreo or above ang verion ng phone
            mChannel = new NotificationChannel(CHANNEL_ID, name, NotificationManager.IMPORTANCE_DEFAULT);

            mChannel.setVibrationPattern(new long[]{0});
            mChannel.enableVibration(true);

            notification = new NotificationCompat.Builder(mContext, CHANNEL_ID)
                    .setSmallIcon(R.drawable.download_icon)
                    .setProgress(0, 0, false);

            notificationManager.createNotificationChannel(mChannel);
        }
    }

    @Override
    protected void onProgressUpdate(Integer... values) {
        super.onProgressUpdate(values);

        Log.d("Avery", values[0] + "");

        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {

            mChannel.setVibrationPattern(new long[]{0});
            mChannel.enableVibration(true);

            notification.setProgress(100, values[0], false);

            //notificationManager.createNotificationChannel(mChannel);

            notificationManager.notify(NOTIFY_ID, notification.build());
        }
    }

    @Override
    protected String doInBackground(String... strings) {
        Log.d("Avery", "Starting Async");

        File gameFile;

        //final String path = Environment.getExternalStorageDirectory() + "//Download//" + "//ChamberDownloads//Books/" + "/" + strings[0] + "//" + strings[0] + ".apk";
        final String absolutePath = Environment.getExternalStorageDirectory().getAbsolutePath();
        final String fileSize = strings[1]; //Eto yung galing sa params ng Asynctask
        Log.d("Avery", Environment.DIRECTORY_DOWNLOADS);
        int count;

        try {
            URL url = new URL(strings[0]);
            URLConnection connection = url.openConnection();

            gameFile = new File(absolutePath, "Game" + ".apk");

            if (!gameFile.exists()) {
                gameFile.getParentFile().mkdirs();
                gameFile.createNewFile();
                Log.d("Avery", "APK does not exists");
            } else {
                Log.d("Avery", "APK  exists");
            }

            int lengthOfFile = connection.getContentLength();
            Log.d("Avery", "Length of file: " + lengthOfFile);

            InputStream inputStream = new BufferedInputStream(url.openStream());
            OutputStream outputStream = new FileOutputStream(gameFile);

            byte data[] = new byte[4096]; ///

            long total = 0;
            int progress = 0;

            while ((count = inputStream.read(data)) != -1) {
                Math.abs(total += count);
                int progress_temp = Math.abs((int) (total * 100) / Integer.parseInt(fileSize));

                if(progress_temp%10 == 0 && progress != progress_temp){
                    progress = progress_temp;
                    Log.v("Avery", "total = "+progress);
                }
                publishProgress(progress);
                // Log.d("Avery", String.valueOf(total));
                outputStream.write(data, 0, count);
            }

            outputStream.flush();
            outputStream.close();
            inputStream.close();
        } catch (Exception e) {
            Log.e("Avery", e.getMessage());
        }
        return null;
    }
}

我希望输出的进度永远不会减少。

1 个答案:

答案 0 :(得分:0)

您的确int溢出了。

(int) (total * 100)一旦total增加到21,474,836,就会溢出。在这一点上,相乘的结果变得大于(2 ^ 31-1),它是可以由int表示的最大正值。由于将long的结果强制转换为int,因此值会自动换行,并且符号可能会翻转。

要解决此问题,只需更改投放顺序,即可在longs上进行计算:

int progress_temp = Math.abs((int) ((total * 100) / Integer.parseInt(fileSize)));