代码之家  ›  专栏  ›  技术社区  ›  martinr

字符串类内部-如果使用UTF-8,则缓存字符到字节的偏移量关系

  •  1
  • martinr  · 技术社区  · 16 年前

    在编写存储的自定义字符串类时 UTF-8 内部(保存内存)而不是 UTF-16 从头开始,当应用程序使用具有随机访问的类时,是否在某种程度上缓存字节偏移量和字符偏移量之间的关系以提高性能?

    Perl是否执行这种字符偏移到字节偏移关系的缓存?python字符串如何在内部工作?

    ObjuleC和Java怎么办?他们内部使用UTF-8吗?

    编辑

    在内部使用UTF-8找到了对Perl5的引用:

    “$flag=utf8::是\u utf8(字符串)

    (自Perl5.8.1以来)在内部测试字符串是否为utf-8。功能上与encode::is_utf8()相同。

    在页面上

    http://perldoc.perl.org/utf8.html

    编辑

    在我想到的应用程序中,字符串在XMPP流中有1-2K XML节。我预计大约有1%的消息将有多达50%(按字符计数)的Unicode值>127(这是XML)。在服务器中,消息被规则检查,并有条件地路由到字段的一个小(按字符量)子集上。服务器是在农场中运行的Wintel设备。在客户机中,数据来自并输入到UI工具包中。

    编辑

    但是这个应用程序不可避免地会发展,并且也希望做一些随机访问。当这种情况发生时,性能会受到影响吗:如果存在更通用的类设计(例如,为大的utf8字符串管理字符偏移量的b-树<->字节偏移量关系),我也会感兴趣(或者在一般情况下,其他一些算法是有效的)。

    3 回复  |  直到 16 年前
        1
  •  2
  •   Dan    16 年前

    Perl区分Unicode和非Unicode字符串。Unicode字符串在内部使用UTF-8实现。非Unicode并不一定意味着7位的ASCII,但是,它可以是任何可以在当前区域设置中表示为单字节的字符。

        2
  •  1
  •   steveha    16 年前

    我认为答案是:总的来说,尝试这样做是不值得的。在你的具体情况下,也许。

    如果您的大多数字符是纯ASCII字符,并且很少有UTF序列,那么用偏移量构建某种稀疏的数据结构可能是值得的。

    在一般情况下,每个字符都可能是非ASCII字符,您可能有许多偏移量要存储。实际上,最常见的情况是创建一个与Unicode字符字符串长度完全相同的字节字符串,并让每个字节值作为下一个字符的偏移量。但这意味着每个字符只需要一个完整的字节,因此每个Unicode字符只需要节省一个字节;这可能不值得做。这意味着索引到字符串现在是一个O(N)操作,因为您运行这些偏移量并求和以找到实际的索引。

    如果您确实想尝试稀疏数据结构,我建议使用一组成对的值,第一个值是字符Unicode字符串中的索引,第二个值是该字符实际出现的字节序列中的索引。然后,在每个utf8转义序列之后,您将添加两个值以查找字符串中的下一个字符。最后,当为unicode字符指定索引时,代码可以对此数组进行二进制搜索,以查找稀疏数组中低于请求索引的最高索引,然后使用该索引查找表示所需字符开头的实际字节。

    如果需要保存内存,可以考虑使用数据压缩库。将unicode字符串作为完整的unicode压缩,然后将其索引为字符串,首先解压缩该字符串。这真的会节省内存,而且要使代码正确地工作是很容易和快速的;但是它可能会增加太多的CPU开销,这是合理的。

        3
  •  1
  •   Daniel Yankowsky    16 年前

    Java的字符串是UTF16内部的:

    字符串表示采用UTF-16格式的字符串,其中补充字符由代理项对表示(有关详细信息,请参阅字符类中的Unicode字符表示部分)。索引值指的是字符代码单位,因此补充字符在字符串中使用两个位置。

    java.lang.String