1use std::fs::File;
2use std::io::{BufReader, Read, Write};
3use std::path::PathBuf;
4
5pub struct ConvertCombine;
6
7const ONE_GB: u64 = 1_073_741_824; impl ConvertCombine {
9
10 pub fn combine_all(paths: Vec<PathBuf>, output: PathBuf) {
11 let mut output_file = match File::create(&output) {
13 Ok(f) => f,
14 Err(e) => {
15 eprintln!("无法创建输出文件 '{}': {}", output.display(), e);
16 return;
17 }
18 };
19
20 for path in paths {
22 let input_file = match File::open(&path) {
24 Ok(f) => f,
25 Err(e) => {
26 eprintln!("跳过文件 [{}]: 打开失败 - {}", path.display(), e);
27 continue;
28 }
29 };
30
31 let metadata = match input_file.metadata() {
33 Ok(m) => m,
34 Err(e) => {
35 eprintln!("跳过文件 [{}]: 获取元数据失败 - {}", path.display(), e);
36 continue;
37 }
38 };
39
40 if metadata.len() > ONE_GB {
42 Self::process_large_file(input_file, &mut output_file, &path);
43 } else {
44 Self::process_small_file(input_file, &mut output_file, &path);
45 }
46
47 if let Err(e) = writeln!(&mut output_file) {
49 eprintln!("跳过文件 [{}]: 写入分隔符失败 - {}", path.display(), e);
50 continue;
51 }
52
53 println!("成功合并文件: {}", path.display());
54 }
55
56 println!("\n合并完成!结果已保存到: {}", output.display());
57 }
58
59 fn process_small_file(input: File, output: &mut File, path: &PathBuf) {
61 let mut contents = String::new();
62 match BufReader::new(input).read_to_string(&mut contents) {
63 Ok(_) => {
64 if let Err(e) = write!(output, "{}", contents) {
65 eprintln!("写入失败 [{}]: {}", path.display(), e);
66 }
67 }
68 Err(e) => eprintln!("读取失败 [{}]: {}", path.display(), e),
69 }
70 }
71
72 fn process_large_file(mut input: File, output: &mut File, path: &PathBuf) {
74 let mut buffer = vec![0u8; 8 * 1024 * 1024]; let mut total = 0;
76
77 loop {
78 let bytes_read = match input.read(&mut buffer) {
79 Ok(0) => break, Ok(n) => n,
81 Err(e) => {
82 eprintln!("读取失败 [{}]: {}", path.display(), e);
83 break;
84 }
85 };
86
87 match output.write_all(&buffer[..bytes_read]) {
88 Ok(_) => total += bytes_read,
89 Err(e) => {
90 eprintln!("写入失败 [{}]: {}", path.display(), e);
91 break;
92 }
93 }
94 }
95
96 println!("已流式传输 {} MB", total / 1024 / 1024);
97 }
98}