java在osx和linux上以不同方式读取文件系统文件名

时间:2016-12-01 09:29:38

标签: java linux macos utf-8 locale

我有一个几乎完美的java程序。我正在开发一个mac并推动linux进行生产。当mac搜索文件系统并将新文件名插入数据库时​​,它工作得很好。但是,当我推送到linux盒子并进行搜索/插入时,它会找到一些带有不同IE字符的文件:BélaFleck。它们在数据库和mac AND linux文件系统中看起来与我相同。事实上,mac和linux盒子有NFS挂载到文件所在的第三个系统(linux)。

我已经转储了字节,可以看到linux和mac如何看到文件系统中的字符串:BélaFleck。

的Linux:

utf8bytes[0] = 0x42
utf8bytes[1] = 0x65
utf8bytes[2] = 0xcc
utf8bytes[3] = 0x81
utf8bytes[4] = 0x6c
utf8bytes[5] = 0x61
utf8bytes[6] = 0x20
utf8bytes[7] = 0x46
utf8bytes[8] = 0x6c
utf8bytes[9] = 0x65
utf8bytes[10] = 0x63
utf8bytes[11] = 0x6b

linux says LANG=en_US.UTF-8

MAC:

utf8Bytes[0] = 0x42
utf8Bytes[1] = 0xc3
utf8Bytes[2] = 0xa9
utf8Bytes[3] = 0x6c
utf8Bytes[4] = 0x61
utf8Bytes[5] = 0x20
utf8Bytes[6] = 0x46
utf8Bytes[7] = 0x6c
utf8Bytes[8] = 0x65
utf8Bytes[9] = 0x63
utf8Bytes[10] = 0x6b

mac says LANG=en_US.UTF-8
试过这个,仍然没有快乐。

java -Dfile.encoding=UTF-8

我正在使用java nio文件来获取目录:

java.nio.file.Path path = Paths.get("test");

然后走

路径
Files.walkFileTree(path, new SimpleFileVisitor<Path>() {

然后,因为这是测试路径中的一个子目录:

 file.getParent().getName(1).toString()

任何人对这里的故障以及如何解决这个问题都有任何想法?

感谢。

2 个答案:

答案 0 :(得分:2)

有些搜索显示OS X总是分解文件名:

这告诉我你可能不小心切换了输出:第一个字节数组被分解,所以我猜测它是从Mac中获取的,而第二个是来自Linux。

无论如何,如果您希望它们对所有系统都相同,您可以自己进行分解:

String name = file.getParent().getName(1).toString();
name = Normalizer.normalize(name, Normalizer.Form.NFD);

答案 1 :(得分:1)

(不是真正的答案,只是更多的讨论。)

这些似乎是utf8字符,但以不同的方式形成。

c4a9é - 这通常是人们输入重音字母的方式。

但是,可以使用一对字符:

65cc91,但形成为e和“COMBINING INVERTED BREVE”的组合。 c3aa是单个字符ê

某些COLLATIONs可以弥补差异,但是应用程序可以在关键时刻将它们组合起来。

SELECT CAST(UNHEX('65cc91') AS CHAR) =
       CAST(UNHEX('c3aa') AS CHAR) COLLATE utf8_unicode_520_ci;  --> 1