1 using System;
2 using System.Collections.Generic;
3 using System.IO;
4 using System.Linq;
5
6 namespace Client
7 {
8 /// <summary>
9 /// 文件切割与合并
10 /// </summary>
11 public class FilePartitions
12 {
13 #region const params
14 private const Int32 DefaultMaxEdges = 5 * 1024; //默认切割边界 5M
15 private String TargetFilePrefix = "part_"; //生成文件的前缀
16 #endregion
17
18 #region private params
19 private Int32 iMaxEdges = 0;
20 private String strTargetDir = String.Empty;
21 private Int32 iFileCount = 0;
22 #endregion
23
24 #region Attribute
25 /// <summary>
26 /// 文件切割边界
27 /// </summary>
28 public Int32 MaxEdges { get { return iMaxEdges > 0 ? iMaxEdges : DefaultMaxEdges; } set { iMaxEdges = value; } }
29
30 /// <summary>
31 /// 切割文件放置位置
32 /// 未设置将与源文件放置同一目录
33 /// </summary>
34 public String TargetDir
35 {
36 get { return String.Empty.Equals(strTargetDir) ? Path.GetDirectoryName(SourceFile) : strTargetDir; }
37 set { strTargetDir = value; }
38 }
39
40 /// <summary>
41 /// 源文件
42 /// </summary>
43 public String SourceFile { get; set; }
44
45 /// <summary>
46 /// 总生成的文件数
47 /// </summary>
48 public Int32 FileCount { get { return iFileCount; } }
49
50 /// <summary>
51 /// 切割后文件前缀
52 /// </summary>
53 public String FilePrefix { get { return TargetFilePrefix; } set { TargetFilePrefix = value; } }
54
55 #endregion
56
57 public FilePartitions()
58 {
59
60 }
61
62 public FilePartitions(String sourceFileName)
63 {
64 SourceFile = sourceFileName;
65 if (!File.Exists(SourceFile))
66 throw new Exception(String.Format("待处理文件 {0} 不存在!", SourceFile));
67 }
68 /// <summary>
69 /// 切割文件为小块文件流
70 /// </summary>
71 /// <param name="filename"></param>
72 /// <returns></returns>
73 public IEnumerator<byte[]> GetFileBytes(string filename)
74 {
75 FileStream sourceStream = null;
76 BinaryReader SplitFileReader = null;
77 int iFileSize = MaxEdges * 1024;
78 byte[] TempBytes;
79 using (sourceStream = new FileStream(SourceFile, FileMode.Open, FileAccess.Read))
80 {
81 using (SplitFileReader = new BinaryReader(sourceStream))
82 {
83 if (sourceStream.Length % iFileSize == 0)
84 {
85 iFileCount = (int)(sourceStream.Length / iFileSize);
86 }
87 else
88 {
89 iFileCount = (int)(sourceStream.Length / iFileSize) + 1;
90 }
91 for (var i = 1; i <= iFileCount; i++)
92 {
93 TempBytes = SplitFileReader.ReadBytes(iFileSize);
94 yield return TempBytes;
95 }
96 }
97 }
98 }
99 /// <summary>
100 /// 切割文件为小块文件流
101 /// </summary>
102 /// <returns></returns>
103 public IEnumerator<byte[]> GetFileBytes()
104 {
105 return GetFileBytes(SourceFile);
106 }
107 /// <summary>
108 /// 合并文件【文件还原】
109 /// </summary>
110 /// <returns></returns>
111 public Boolean OnMergeFiles()
112 {
113 Boolean bResult = true;
114 FileStream AddStream = null;
115 BinaryWriter AddWriter = null;
116 FileStream TempStream = null;
117 BinaryReader TempReader = null;
118 try
119 {
120
121 string[] arrFileNames = Directory.GetFiles(TargetDir);
122 List<FileInfoExt> fileInfo = new List<FileInfoExt>();
123 foreach (String fileName in arrFileNames)
124 {
125 String f1 = Path.GetFileName(fileName);
126 if (f1.IndexOf(FilePrefix) == 0)
127 fileInfo.Add(new FileInfoExt() { FileFullname = fileName, Filename = f1, FileCrTime = File.GetLastWriteTime(fileName) });
128 }
129 fileInfo = fileInfo.OrderBy(p => p.FileCrTime).ToList();
130 iFileCount = fileInfo.Count;
131
132 AddStream = new FileStream(SourceFile, FileMode.OpenOrCreate);
133 AddWriter = new BinaryWriter(AddStream);
134
135 foreach (FileInfoExt fileName in fileInfo)
136 {
137 TempStream = new FileStream(fileName.FileFullname, FileMode.Open, FileAccess.Read);
138 TempReader = new BinaryReader(TempStream);
139 AddWriter.Write(TempReader.ReadBytes((int)TempStream.Length));
140 TempReader.Close();
141 TempReader.Close();
142 }
143
144 }
145 catch (Exception ex)
146 {
147 bResult = false;
148 throw ex;
149 }
150 finally
151 {
152 if (TempReader != null) TempReader.Close();
153 if (TempStream != null) TempStream.Close();
154 if (AddStream != null) AddStream.Close();
155 if (AddWriter != null) AddWriter.Close();
156 }
157 return bResult;
158 }
159 }
160
161 public class FileInfoExt
162 {
163 /// <summary>
164 /// 文件完整路径
165 /// </summary>
166 public String FileFullname { get; set; }
167 /// <summary>
168 /// 文件名
169 /// </summary>
170 public String Filename { get; set; }
171 /// <summary>
172 /// 最后修改时间
173 /// </summary>
174 public DateTime FileCrTime { get; set; }
175
176 }
177
178 }