Java如何实现Tab分隔txt表格按多列优先级高效排序?
Java实现Tab分隔文本文件多列自定义规则排序
核心思路
基于Java 8+的Comparator链式拼接能力实现多列优先级排序,自定义单值比较逻辑满足「数字>字母、数字升序、字母按字典序」的规则,整体时间复杂度为O(n log n),可应对GB级以下普通规模的文本文件。
完整实现代码
import java.io.IOException; import java.nio.file.Files; import java.nio.file.Path; import java.util.ArrayList; import java.util.Comparator; import java.util.List; import java.util.stream.Collectors; public class TabFileSorter { // 自定义单值比较规则:数字优先级高于字母,数字升序,字母按字典序排序 private static int compareValue(String a, String b) { boolean isANum = isNumeric(a); boolean isBNum = isNumeric(b); // 都是数字:按数值升序 if (isANum && isBNum) { return Long.compare(Long.parseLong(a), Long.parseLong(b)); } // a是数字b不是:a排前面 if (isANum) { return -1; } // b是数字a不是:b排前面 if (isBNum) { return 1; } // 都是字母:按自然字典序排序,需要不区分大小写可换成String.CASE_INSENSITIVE_ORDER.compare(a,b) return a.compareTo(b); } // 判断字符串是否为整数,有小数需求可替换为BigDecimal的尝试转换逻辑 private static boolean isNumeric(String str) { if (str == null || str.isEmpty()) { return false; } try { Long.parseLong(str); return true; } catch (NumberFormatException e) { return false; } } public static void sortTabFile(String inputPath, String outputPath) throws IOException { // 1. 读取文件所有行,过滤空行 List<String[]> rows = Files.lines(Path.of(inputPath)) .filter(line -> !line.isBlank()) .map(line -> line.split("\t")) .collect(Collectors.toCollection(ArrayList::new)); if (rows.isEmpty()) { Files.writeString(Path.of(outputPath), ""); return; } // 2. 构造多列链式比较器:按列顺序依次比较,前一列相等才比较后一列 Comparator<String[]> comparator = (row1, row2) -> compareValue(row1[0], row2[0]); int maxColumn = rows.get(0).length; for (int i = 1; i < maxColumn; i++) { int columnIndex = i; comparator = comparator.thenComparing(row -> row[columnIndex], TabFileSorter::compareValue); } // 3. 排序 rows.sort(comparator); // 4. 拼接为Tab分隔的行,写入输出文件 List<String> outputLines = rows.stream() .map(row -> String.join("\t", row)) .collect(Collectors.toList()); Files.write(Path.of(outputPath), outputLines); } public static void main(String[] args) throws IOException { // 替换为你的输入输出文件路径 sortTabFile("input.txt", "output.txt"); } }
说明
- 支持任意列数的自动排序,不需要手动指定列数,会自动按从左到右的列优先级比较
- 如果你的文件列值包含小数,只需修改
isNumeric和compareValue中数字转换的逻辑为BigDecimal即可 - 超大文件(GB级以上)建议采用外部排序方案,即拆分文件为多个小文件排序后再合并,避免内存溢出
内容的提问来源于stack exchange,提问作者Глеб Карпук
相关产品推荐
相关产品推荐

