zoukankan      html  css  js  c++  java
  • Java中解压文件名有中文的rar包出现乱码问题的解决

      1 import java.io.File;
      2 import java.io.FileNotFoundException;
      3 import java.io.FileOutputStream;
      4 import java.io.IOException;
      5 import java.io.InputStream;
      6 import java.util.Enumeration;
      7 import java.util.zip.ZipEntry;
      8 import java.util.zip.ZipFile;
      9 import de.innosystec.unrar.Archive;
     10 import de.innosystec.unrar.exception.RarException;
     11 import de.innosystec.unrar.rarfile.FileHeader;
     12 
     13 /**
     14  * 对rar或者zip进行解压缩
     15  * 
     16  * @author yKF41624
     17  * 
     18  */
     19 public class Decompress {
     20     private static String fileName = "";
     21 
     22     /**
     23      * 对rar文件解压
     24      * 
     25      * @param rarFileName
     26      * @param extPlace
     27      * @return
     28      */
     29     public static boolean unrarFiles(String rarFileName, String extPlace) {
     30         boolean flag = false;
     31         Archive archive = null;
     32         File out = null;
     33         File file = null;
     34         File dir = null;
     35         FileOutputStream os = null;
     36         FileHeader fh = null;
     37         String path, dirPath = "";
     38         try {
     39             file = new File(rarFileName);
     40             archive = new Archive(file);
     41         } catch (RarException e1) {
     42             e1.printStackTrace();
     43         } catch (IOException e1) {
     44             e1.printStackTrace();
     45         } finally {
     46             if (file != null) {
     47                 file = null;
     48             }
     49         }
     50         if (archive != null) {
     51             try {
     52                 fh = archive.nextFileHeader();
     53                 while (fh != null) {
     54                     fileName = fh.getFileNameString().trim();
     55                     path = (extPlace + fileName).replaceAll("\\", "/");
     56                     int end = path.lastIndexOf("/");
     57                     if (end != -1) {
     58                         dirPath = path.substring(0, end);
     59                     }
     60                     try {
     61                         dir = new File(dirPath);
     62                         if (!dir.exists()) {
     63                             dir.mkdirs();
     64                         }
     65                     } catch (RuntimeException e1) {
     66                         e1.printStackTrace();
     67                     } finally {
     68                         if (dir != null) {
     69                             dir = null;
     70                         }
     71                     }
     72                     if (fh.isDirectory()) {
     73                         fh = archive.nextFileHeader();
     74                         continue;
     75                     }
     76                     out = new File(extPlace + fileName);
     77                     try {
     78                         os = new FileOutputStream(out);
     79                         archive.extractFile(fh, os);
     80                     } catch (FileNotFoundException e) {
     81                         e.printStackTrace();
     82                     } catch (RarException e) {
     83                         e.printStackTrace();
     84                     } finally {
     85                         if (os != null) {
     86                             try {
     87                                 os.close();
     88                             } catch (IOException e) {
     89                                 e.printStackTrace();
     90                             }
     91                         }
     92                         if (out != null) {
     93                             out = null;
     94                         }
     95                     }
     96                     fh = archive.nextFileHeader();
     97                 }
     98             } catch (RuntimeException e) {
     99                 e.printStackTrace();
    100             } finally {
    101                 fh = null;
    102                 if (archive != null) {
    103                     try {
    104                         archive.close();
    105                     } catch (IOException e) {
    106                         e.printStackTrace();
    107                     }
    108                 }
    109             }
    110             flag = true;
    111         }
    112         return flag;
    113     }
    114 }

     以上代码解压无中文的压缩包是很正常的,经过调试发现,是在的文件名的时候如果含有中文那么得到的就是乱码,即是代码中的第54行:

    Java代码  收藏代码
    1. fileName = fh.getFileNameString().trim();  

    最开始我查了下API,我发现有一个getFileNameW()方法,就尝试着用这个方法得到要解压的文件名,发现如果有中文一下就成功了,于是 我把上面的方法替换成了这个,可是没想到如果来的压缩包没有英文,那么就得不到了,于是这就要加个判断。于是我通过正则表达式判断文件名中是否含有中文, 如果有中文,调用getFileNameW(),如果没有中文就调用getFileNameString()方法,就解决了。

    附上判断字符中是否存在中文的方法:

    1. public static boolean existZH(String str) {  
    2.     String regEx = "[\u4e00-\u9fa5]";  
    3.     Pattern p = Pattern.compile(regEx);  
    4.     Matcher m = p.matcher(str);  
    5.     while (m.find()) {  
    6.         return true;  
    7.     }  
    8.     return false;  
    9. }  

    于是,只需要将原来的代码第54行修改为如下代码即可:

    fileName=  fh.getFileNameW().trim();                 
    if(!existZH(fileName)){                    
      fileName = fh.getFileNameString().trim();                 
    网友评论更好办法:
    主要是55行,由于没有对extPlace 和 fileName进行路径分割符进行替换,导致后面使用fileName的时候,还是会出现文件名中含有""分隔符。所以,在55行前,我添加了一下两句:
    extPlace = extPlace.replaceAll("\\", File.separator);
    fileName = fileName.replaceAll("\\", File.separator);
    问题解决。
    extPlace = extPlace.replaceAll("\\", File.separator);
    fileName = fileName.replaceAll("\\", File.separator);
     
     File.separator在windows系统与unix系统里的值分别是什么?  windows是,unix是/
    
    
    http://yangjingblog.iteye.com/blog/1134030
  • 相关阅读:
    开发了套三维光学扫描仪,可以技术转让
    见微知著 带你透过内存看 Slice 和 Array的异同
    Goland 这些技巧,学会开发效率翻倍!
    不懂汇编,也能看懂的 Go interface 原理分析
    win10创建删除文件文件夹需刷新才更新问题
    转载:java中DAO层、Service层、Control层的说明
    代码习惯
    查看网站的服务器和使用的技术
    flutter: CSS规则映射flutter控件-position
    android对话框透传Touch事件
  • 原文地址:https://www.cnblogs.com/sunxucool/p/3140749.html
Copyright © 2011-2022 走看看