如何检测用户的语言环境以获取正确的 csv 分隔符?

Posted

技术标签:

【中文标题】如何检测用户的语言环境以获取正确的 csv 分隔符?【英文标题】:How do I detect the user's locale to get the correct csv separator? 【发布时间】:2011-11-11 10:34:38 【问题描述】:

我有一个简单的数据转换工具,它可以产生的输出之一是 csv 文件。

这在英国非常有效,但是当我将它运送给德国客户时,我遇到了一些问题。具体来说,他们使用“,”来表示浮点数中的小数点,反之亦然。这意味着当他们在 excel 中打开他们的数据文件时,至少可以说结果相当混乱:-)

替换正确的字符是微不足道的,但我如何检测是否应用它?

编辑:

所以这个:

a,b,c
1.1,1.2,1.3
"1.1",1,2,"1,3"
"this,is,multi-
-line",this should be column 2, row 4
a;b;c
"a;b","c"

..在英国加载到 excel 时是这样的:

+----------------+-----+-----+-----+
| a              | b   | c   |     |
+----------------+-----+-----+-----+
| 1.1            | 1.2 | 1.3 |     |
+----------------+-----+-----+-----+
| 1.1            | 1   | 2   | 1,3 |
+----------------+-----+-----+-----+
| this,is,multi- |     |     |     |
| -line          | 2   | 4   |     |
+----------------+-----+-----+-----+
| a;b;c          |     |     |     |
+----------------+-----+-----+-----+
| a;b            | c   |     |     |
+----------------+-----+-----+-----+

..但是在德国会发生什么?

【问题讨论】:

csv 分隔符 依赖于语言环境:它只是文件格式的属性;如上所述,您应该引用或转义出现在单元格值中的任何分隔符 道歉;我不知道该怎么表达。所以这是我需要正确处理的小数分隔符?我的客户建议他们使用分号作为 .csv 文件的分隔符...? 查看***以获取有关 'c'sv 文件的参考:en.wikipedia.org/wiki/Comma-separated_values ...这表明在德国他们使用分号...? 荷兰和德国都使用这两种格式 - 但是分号格式并不严格遵循 RFC,建议使用逗号,并在任何需要转义的值上加上双引号。 重新编辑:德国/荷兰现在应该与英国相同。 (即一个文件只能有一个分隔符,一旦设置了逗号,分号将被视为另一个字符。 【参考方案1】:

用途:

System.Globalization.CultureInfo.CurrentCulture.TextInfo.ListSeparator

编写 CSV:“列表分隔符”字符串应用作 CSV 中的分隔符(请参阅下文了解如何更改此变量)。当另存为 CSV 时,更改“列表分隔符”的值也会反映在 Excel 中。

阅读 CSV:确定 CSV 中的分隔符是另一回事,它有点复杂。原则上,可以在一个系统中使用“,”作为 CSV 分隔符并使用“;”甚至是“*”或任何(“字符串”)作为另一个系统上的分隔符:本文提供了一些关于如何检测读取跨系统 CSV 文件的 CSV 分隔符的见解:

http://www.codeproject.com/Articles/231582/Auto-detect-CSV-separator。

您还可以通过更改 Windows 中的“列表分隔符”值来对导出器执行一些测试,如下所示(每个 Windows 操作系统可能不同):

打开区域和语言对话框。 在“格式”选项卡上选择。 点击“其他设置” 编辑“列表分隔符”的值

【讨论】:

【参考方案2】:

正如其他人提到的,CSV 通常应该用逗号分隔,并且字段应该用双引号引起来。然而,也有 MS Excel 特定的行为会导致正确的 CSV 文件被错误地导入。这是因为 MS Excel 默认使用 Windows 系统中“区域和语言选项”中设置的列表分隔符。对于美国/英国语言环境,它是逗号,但对于德语等语言,它是分号。因此,对于 MS Excel,选项是为每个语言环境使用不同的分隔符。

【讨论】:

【参考方案3】:

CurrencyDecimalSeparator 属性包含给定区域性的小数分隔符。这就是说 CSV 分隔符不依赖于文化。它是您向解析器指示的 CSV 文件的属性。谈到解析器,我真诚地希望你是not rolling your own CSV parser。

【讨论】:

这是我继承的遗留代码库,它只是我正在处理的输出,而不是将其解析为输入。我们实际上在需要的地方使用 lumen 作品进行 csv 解析:codeproject.com/KB/database/CsvReader.aspx【参考方案4】:

正如其他人已经建议的那样,格式不应区分区域设置。 这适用于存储(在 CSV 或其他格式的文件中)或通信协议。您应该只担心表示层的区域设置敏感性。 否则,这意味着由美国用户(例如)保存的文件无法由德国用户(反之亦然)加载。

查看此处了解更完整的指南:http://mihai-nita.net/2005/10/25/data-internationalization/

【讨论】:

【参考方案5】:

我阅读这个问题的方式是问题不在于 .csv 文件。 .csv 文件的格式可能对所有用户都相同,正如上面每个答案中重复的那样。

但是,Excel VBA 应用程序对区域设置敏感。

当不同国家的不同用户打开 Excel 时,他们使用现有的区域设置,有时与 .csv 文件不同,因此以不同的方式解释 .csv 文件中的数据。

所以问题真的是,我们如何围绕它进行编程,以便我们的代码提取当前的区域分隔符,然后执行正确的解释?

一种方法是编写一个小代码 sn-p 将十进制数写入测试单元,然后将其读回以查看使用了什么十进制,但应该有更简洁的方法来做到这一点...

【讨论】:

这是一个有用的部分答案。请避免给人以这是您添加的问题的印象。此处回答帖子应仅回答此页面顶部的问题。【参考方案6】:

顾名思义,CSV 文件应以逗号分隔,并且不依赖于本地。然而,为了避免这个问题,您可以做的是双引号 CSV 文件中的相关十进制数字:"10,20", "1,50", "This is another column"。对于任何像 10,201,50 而不是:1020150

见CSV:

更复杂的 CSV 实现允许逗号和其他特殊的 字段值中的字符。许多实现使用“(双引号) 包含保留字符的值周围的字符(例如 逗号、双引号或换行符);嵌入的双引号字符 可以用一对连续的双引号来表示

【讨论】:

谢谢;用引号括起来看起来好像在英国可以使用,所以我认为它应该允许在浮点字段中使用逗号。干杯! “应该用逗号分隔,并且不依赖于本地......” - 你应该告诉微软! Excel 使用区域和语言设置中定义的“列表分隔符”字符。 正如 druciferre 所说,Microsoft 使用文化配置导出 CSV。因此分隔符并不总是';'。 那很好,你有没有在英语环境以外的环境中看到过微软的excel?例如。捷克语言环境? (默认由';'分隔)

以上是关于如何检测用户的语言环境以获取正确的 csv 分隔符?的主要内容,如果未能解决你的问题,请参考以下文章

我应该如何检测文本文件中使用了哪个分隔符?

如何重新格式化 CSV 文件以匹配正确的 CSV 格式

为 pandas.read_csv 指定正确的 dtypes 以获取日期时间和布尔值

结对-英文词频检测程序-需求分析

用C语言写CSV文件,如何写出多个工作表?

如何在 CSV 文件中的公式中转义逗号