解压缩过程使设备无响应

时间:2012-08-12 13:10:35

标签: java android unzip

在运行下面的代码解压缩70 MB的zip文件(包含750个文件)时,设备无响应并几乎崩溃。谁能告诉我它有什么问题:

boolean UNZipFiles() {
    float prev = -1; // to check if the percent changed and its worth updating the UI
    int finalSize = 0;
    float current = 0;

    try {
        final int BUFFER = 2048;
        String zipFilePath = PATH + FileName;

        BufferedOutputStream dest = null;
        BufferedInputStream is = null;
        ZipEntry entry;
        ZipFile zipfile = new ZipFile(zipFilePath);

        finalSize = (int) new File(zipFilePath).length();

        Enumeration<? extends ZipEntry> e = zipfile.entries();
        while (e.hasMoreElements()) {
            entry = e.nextElement();
            current += entry.getCompressedSize();

            if (entry.isDirectory())
                dirChecker(entry.getName());
            else {
                int count;
                byte data[] = new byte[BUFFER];

                is = new BufferedInputStream(zipfile.getInputStream(entry));
                FileOutputStream fos = new FileOutputStream(PATH + entry.getName());
                dest = new BufferedOutputStream(fos, BUFFER);
                while ((count = is.read(data, 0, BUFFER)) != -1)
                    dest.write(data, 0, count);

                if (prev != current / finalSize * 100) {
                    prev = current / finalSize * 100;

                    UpdatePercentNotificationBar((int) prev);
                }

                dest.flush();
                dest.close();
                is.close();
            }
        }


        DeleteZip(zipFilePath);

        success = true;
    } catch (Exception e) {
        NotificationBarFail("Error while Downloading");
        return false;
    }

    return true;

}

通知管理:

public void onCreate() {        
    super.onCreate();
    mContext = this;

    Intent intent = new Intent(this, Main.class);
    pendingIntent = PendingIntent.getActivity(getApplicationContext(), 0, intent, 0);
    notification = new Notification(R.drawable.icon, "Downloading files", System.currentTimeMillis());
    notification.flags = notification.flags | Notification.FLAG_ONGOING_EVENT;
    notification.contentView = new RemoteViews(getApplicationContext().getPackageName(), R.layout.background_service);
    notification.contentIntent = pendingIntent;
    notification.contentView.setImageViewResource(R.id.status_icon, R.drawable.icon);
    notification.contentView.setTextViewText(R.id.status_Percentage, "0%");
    notification.contentView.setProgressBar(R.id.status_progress, 100, progress, false);

    notificationManager = (NotificationManager) getApplicationContext().getSystemService(NOTIFICATION_SERVICE);

    notificationManager.notify(42, notification);
    FileName = Main.Main_File_Name;
}

新代码:

boolean UNZipFiles() {
        byte[] buffer = new byte[4096];
        int length;
        float prev = -1; // to check if the percent changed and its worth updating the UI
        int finalSize = 0;
        float current = 0;

        try {

            String zipFile = PATH + FileName;

            FileInputStream fin = new FileInputStream(zipFile);
            ZipInputStream zin = new ZipInputStream(fin);

            finalSize = (int) new File(zipFile).length();

            ZipEntry ze = null;

            while ((ze = zin.getNextEntry()) != null) {
                current += ze.getCompressedSize();
                if (ze.isDirectory())
                    dirChecker(ze.getName());
                else {
                    FileOutputStream fout = new FileOutputStream(PATH + ze.getName());
                    while ((length = zin.read(buffer)) > 0)
                        fout.write(buffer, 0, length);
                    if (prev != current / finalSize * 100) {
                        prev = current / finalSize * 100;

                        UpdatePercentNotificationBar((int) prev);
                    }
                    zin.closeEntry();
                    fout.close();
                }

            }
            zin.close();
            DeleteZip(zipFile);


            success = true;
        } catch (Exception e) {
            NotificationBarFail("Error while downloading");
            return false;
        }

        return true;

    }

1 个答案:

答案 0 :(得分:1)

在代码中,您调用UpdatePercentNotificationBar的部分超过100次,因为您使用了prev的浮点值,因此每个循环都会生成一条新消息。

原件:

float prev;
...
if (prev != current / finalSize * 100) {
  prev = current / finalSize * 100;
  UpdatePercentNotificationBar((int) prev);
}

应该是这样的:

int prev;
...
if (prev != (int)(current / finalSize * 100)) {
  prev = (int)(current / finalSize * 100);
  UpdatePercentNotificationBar(prev);
}

正如您通过更改此逻辑所证实的那样,您不再使用消息充斥UI。