注意:这里说的就是“物理分割”,是真的会把文件分开
不多说,直接上代码
1 import java.io.File;
2 import java.io.FileInputStream;
3 import java.io.FileOutputStream;
4 import java.io.IOException;
5 import java.io.InputStream;
6 import java.io.OutputStream;
7
8 /*
9 *功能:将800M以上大文件(不分类型)切割成为2M/ per part
10 *@date:2018/7/9/23:31
11 *@author:Yoci
12 */
13 public class GeAndZhuang{
14 public static void sCut(File f, int partSize) {
15 if(f.length()>2048*1024) {
16 System.out.println("启动成功");
17 int count = (int)(Math.ceil(f.length() / partSize))+1;//块数
18 System.out.println("块数"+count);
19 try {
20 /**创建输入输出流对象*/
21 InputStream inf = new FileInputStream(f);
22 System.out.println("输入流启动成功");
23 OutputStream[] outf = new FileOutputStream[count];
24 System.out.println("输出流启动成功:"+outf.length);
25 /**创建文件夹,存储各小块文件*/
26 int no = f.getName().lastIndexOf(".");
27 String str = f.getParent()+"\\"+f.getName().substring(0, no );/**目录路径*/
28 File dirfile = new File(str);
29 if(!dirfile.exists()) {
30 dirfile.mkdirs();
31 }
32 /**创建各小块文件并命名*/
33 File[] dir_f = new File[count];
34 System.out.println("数组创建成功:"+dir_f.length);
35 /**获取文件类型*/
36 String fName = f.getName();
37 String fPattern = fName.substring(fName.lastIndexOf("."), fName.length());
38 System.out.println("文件类型获取成功:"+fPattern);
39 for(int j=0; j<count; j++) {
40 String newPath = str+"\\"+f.getName().substring(0, no)+"-"+j+fPattern;
41 dir_f[j] = new File(newPath);
42 outf[j] = new FileOutputStream(dir_f[j]);
43 }
44 /**写入各块内容*/
45 int s,m=0, n=2*1024*1024;
46 byte[] buffer = new byte[n];
47 s = inf.read(buffer, 0, n);
48 while(s != -1&& m<count) {
49 if(dir_f[m].length() < 2048*1024) {
50 outf[m].write(buffer, 0, n);
51 s = inf.read(buffer, 0, n);
52 }
53 if(dir_f[m].length() == 2048*1024){
54 outf[m].close();
55 m = m+1;
56 int off = (int)(f.length()-m*2048*1024);
57 if(off<2048*1024) {
58 outf[m].write(buffer, 0, off);
59 outf[m].close();
60 break;
61 }
62 }
63 }
64 inf.close();
65 f.delete();
66 }
67 catch(IOException ioe) {
68 System.out.println("IO 异常");
69 }
70 catch(IndexOutOfBoundsException ine) {
71 System.out.println("数组越界 异常");
72 }
73 catch(Exception e) {
74 System.out.println("异常");
75 }
76 }
77 else {
78 System.out.println("启动失败");
79 }
80 }
81 public static void divide( String fPath ) {
82 File f = new File(fPath);
83 /**文件存在*/
84 if(f.exists()){
85 /**是单个文件*/
86 if(f.isFile() && f.length() > 2048*1024) {
87 /**调用单文件分割方法*/
88 sCut(f, 2048*1024);
89 }
90 /**是目录*/
91 else if(f.isDirectory() && f.length() > 2048*1024) {
92 /**目录文件数组化*/
93 File[] dir = f.listFiles();
94
95 for(int i=0; i<dir.length; i++) {
96 if(dir[i].exists() && dir[i].length() > 2048*1024){
97 if(dir[i].isFile()) {
98 sCut(dir[i], 2048*1024);
99 }
100 else if(dir[i].isDirectory() && dir[i].length() > 2048*1024) {
101 divide(dir[i].getAbsolutePath());
102 }
103 }
104 else {
105 System.out.println(dir[i].getAbsolutePath()+ "文件或目录较小,无需处理!");
106 }
107 }
108 }
109 }
110 else {
111 System.out.println(fPath + " 不存在,分割失败!");
112 }
113 }
114 /**
115 *小块组装/还原
116 *@param fPath 待组装的文件/目录绝对路径
117 *@return null
118 *思路:扫描文件/目录,当遇到内部文件以 文件夹名 命名且予以编号时,合并文件夹内所有文件并覆盖此文件夹
119 *result:文件/目录属性与分割前相同
120 */
121 public static void pack( String fPath ) {
122 File f = new File(fPath);
123 boolean flag = false;
124 int t, num = 0;
125 if(f.exists()){
126 if(f.isDirectory()) {
127 File[] dir = f.listFiles();
128 for(t=0; t<dir.length; t++) {
129 if(dir[t].isFile()) {
130 if(dir[t].getName().lastIndexOf("-") != -1) {
131 String cutName = dir[t].getName().substring(0, dir[t].getName().lastIndexOf("-"));
132 if(f.getName().compareTo(cutName) == 0) {
133 flag = true;
134 num += 1;
135 }
136 else {
137 flag = false;
138 }
139 }
140 }
141 else if(dir[t].isDirectory()) {
142 pack(dir[t].getAbsolutePath());
143 }
144 }
145 /**组装开始*/
146 if(flag == true && num == dir.length) {
147 try {
148 /**重新构建路径=文件夹路径+后缀*/
149 String dirName = dir[0].getName();
150 int begin = dirName.lastIndexOf(".");
151 String coverPath = f.getAbsolutePath() + dirName.substring(begin, dirName.length());
152 File coverFile = new File(coverPath);
153
154 /**构建输入输出流:
155 * 输入流:packIn dir 文件夹中的编号文件
156 * 输出流:packOut coverFile
157 */
158 OutputStream packOut = new FileOutputStream(coverFile, true);
159 int sizeOfDir = dir.length;
160 for(t=0; t< sizeOfDir; t++)
161 {
162 for(int k=0; k<sizeOfDir; k++) {
163 int b = dir[k].getName().lastIndexOf("-");
164 int e = dir[k].getName().lastIndexOf(".");
165 /**找到与 序号匹配的 文件 写入*/
166 if(dir[k].getName().substring(b+1, e) .compareTo(String.valueOf(t))==0) {
167 //System.out.println(t+" "+ dir[k].getName().substring(b+1, e));
168 InputStream packIn = new FileInputStream(dir[k]);
169 int s, n=2*1024*1024;
170 byte[] buffer = new byte[n];
171 s = packIn.read(buffer, 0, n);
172 if(dir[k].length()==2*1024*1024) {
173 packOut.write(buffer, 0, n);
174 packIn.close();
175 dir[k].delete();
176 }
177 else {
178 int end = (int)dir[k].length();
179 packOut.write(buffer, 0, end);
180 packIn.close();
181 dir[k].delete();
182 }
183 break;
184 }
185 }
186 }
187 packOut.close();
188 System.out.println("文件数:"+dir.length);
189 f.delete();
190 }
191 catch(Exception e) {
192 System.out.println("异常");
193 }
194 }
195 }
196 }
197 }
198 public static void main(String[] args) {
199 String path = "F:\\2221511550\\Videos\\26.20 - 副本.mp4";//要切割的文件/目录路径
200 divide(path);//切割
201 pack("F:\\2221511550\\Videos\\26.20 - 副本");//组装(给出路径)
202 }
203 }