【问题标题】:String.to_atom hardcodes the underlying erlang.binary_to_atom encoding option to :utf8, why?String.to_atom 将底层的 erlang.binary_to_atom 编码选项硬编码为 :utf8,为什么?
【发布时间】:2018-03-22 09:22:29
【问题描述】:

为什么 String.to_atom 将编码选项硬编码为 :utf8 ?

https://github.com/elixir-lang/elixir/blob/d6bb3342b7ea8b921b3d4b69f65064c4158c99d7/lib/elixir/lib/string.ex#L1927 def to_atom(string) do :erlang.binary_to_atom(string, :utf8) end

erlang binary_to_atom 的可用编码选项有:

latin1 | unicode | utf8 http://erlang.org/documentation/doc-8.0-rc1/erts-8.0/doc/html/erlang.html#binary_to_atom-2

【问题讨论】:

    标签: erlang elixir


    【解决方案1】:

    TL;DR

    因为 Erlang 世界终于在所有地方都采用 UTF-8。

    讨论

    latin1 即将消失,主要是 UTF-8 的一个子集(少数字符除外),unicodeutf8 的旧别名,这给我们留下了一个普遍适用的选项:@987654325 @。这一点很重要,因为 UTF-8 原子(和字符串)是 Erlang 和 Elixir 的前进方向。

    如果您使用非 UTF-8 编码处理旧数据,请在调用 binary_to_atom/2 之前将其转换为

    这也符合 Erlang 标准库中较新的 stringunicode 模块更改——在经历了数十年的不确定性之后,这最终可以将 UTF-8 作为普遍接受的标准(因为编码很困难,并且在 Erlang 发明时并没有太多的共识)。

    关于编码实践的一句话

    我在日本工作,主要处理业务数据,其中一些非常古老,还有一些非常疯狂的编码。我倾向于主要使用 Erlang 编写代码(我更喜欢小型语言)。当一些较旧的字符串处理函数和 unicode 模块被编写时,字符串分为两类:

    • ASCII 码点列表(在相当长一段时间内,它被隐式扩展为包含 latin1,因为当时欧洲语言很常见,而 CJK 在当时是一团糟)
    • 龙火僵尸和冰霜僵尸的噩梦(因为对其他任何事情的共识为零,以及大量根本不完整、半生不熟、技术上不准确的“标准”)

    时代变了。现在我们知道字符串几乎总是采用 UTF-8 格式,而 Unixverse 中的一切最终都解决了这个问题,这产生了令人愉快的效果,让(几乎)所有其他有意义的系统也解决了这个问题(如果不是在内部) ,然后通过可以在 UTF-16 和 UTF-8 之间进行选择的强大检测库)。

    您实际上确实拥有非 UTF-8 数据的情况那么您就知道是这种情况,并且应该在将数据发送到通用函数之前对其进行转换比如binary_to_atom/2。实际上,我认为我们应该转移到包括 binary_to_atom/1 并完全淘汰 binary_to_atom/2 -- 从 Erlang R20 开始的 which is what has already happened with list_to_atom/1(耶!)。

    那么这对您的代码有何影响?

    当您开始处理古老的编码时,您的代码的复杂性突然爆炸,需要立即加以控制,以免它疯狂地感染您的整个代码库。做到这一点的最好方法是将疯狂的业务系统保持在适当的外部,并在边缘进行转换。每当我们处理以疯狂编码出现的旧数据时我们已经知道并为此做好了准备——因此我们会立即明确地转换为 UTF-8,因此以后不会遇到任何问题在系统的更深处。

    您可能会想,“为什么他们不检测每个字符串的编码?”唉,没有正确的方法来检测字符串编码。在高度自信的情况下这是不可能的。在大多数情况下,它也很快成为一项过时的任务,因为今天生成的绝大多数数据都是 UTF-8(或 UTF-16,但通过网络遇到这种情况非常罕见)。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-01-05
      • 2017-08-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-10-07
      相关资源
      最近更新 更多