8个稳定版本

使用旧的Rust 2015

1.20141219.5 2015年4月14日
1.20141219.4 2015年4月3日
1.20141219.2 2015年3月26日
1.20141219.1 2015年1月29日
1.0.20140915 2014年11月14日

#1743 in 文本处理

Download history 73188/week @ 2024-03-14 71785/week @ 2024-03-21 55396/week @ 2024-03-28 65388/week @ 2024-04-04 56420/week @ 2024-04-11 64982/week @ 2024-04-18 60559/week @ 2024-04-25 53461/week @ 2024-05-02 53597/week @ 2024-05-09 59779/week @ 2024-05-16 55355/week @ 2024-05-23 55224/week @ 2024-05-30 55075/week @ 2024-06-06 52994/week @ 2024-06-13 51373/week @ 2024-06-20 39196/week @ 2024-06-27

208,505 个月的下载量
用于 编码

CC0 许可证

115KB
1.5K SLoC

编码 0.3.0-dev

Encoding on Travis CI

为Rust提供字符编码支持。(也称为 rust-encoding)它基于 WHATWG 编码标准,并提供错误检测和恢复的高级接口。

本文档是针对开发版本(0.3)。有关0.2.x版本的稳定文档,请参阅 稳定文档

完整文档(稳定版)

用法

将以下内容放入您的 Cargo.toml

[dependencies]
encoding = "0.3"

然后在您的crate根目录中放入以下内容

extern crate encoding;

数据表

默认情况下,Encoding附带约480 KB的数据表("索引")。这允许Encoding高效地编码和解码旧编码,但这可能不适合某些应用程序。

Encoding提供了 no-optimized-legacy-encoding Cargo功能,以降低编码表的大小(至约185 KB),但会牺牲编码性能(通常慢5倍到20倍)。解码性能保持不变。此功能强烈建议供最终用户使用。永远不要尝试从库crate启用此功能。

有关更精细的优化,请参阅 src/index/gen_index.py 以生成自定义表。

概述

要编码字符串

use encoding::{Encoding, EncoderTrap};
use encoding::all::ISO_8859_1;

assert_eq!(ISO_8859_1.encode("caf\u{e9}", EncoderTrap::Strict),
           Ok(vec![99,97,102,233]));

要编码包含无法表示的字符的字符串

use encoding::{Encoding, EncoderTrap};
use encoding::all::ISO_8859_2;

assert!(ISO_8859_2.encode("Acme\u{a9}", EncoderTrap::Strict).is_err());
assert_eq!(ISO_8859_2.encode("Acme\u{a9}", EncoderTrap::Replace),
           Ok(vec![65,99,109,101,63]));
assert_eq!(ISO_8859_2.encode("Acme\u{a9}", EncoderTrap::Ignore),
           Ok(vec![65,99,109,101]));
assert_eq!(ISO_8859_2.encode("Acme\u{a9}", EncoderTrap::NcrEscape),
           Ok(vec![65,99,109,101,38,35,49,54,57,59]));

要解码字节序列

use encoding::{Encoding, DecoderTrap};
use encoding::all::ISO_8859_1;

assert_eq!(ISO_8859_1.decode(&[99,97,102,233], DecoderTrap::Strict),
           Ok("caf\u{e9}".to_string()));

要解码包含无效序列的字节序列

use encoding::{Encoding, DecoderTrap};
use encoding::all::ISO_8859_6;

assert!(ISO_8859_6.decode(&[65,99,109,101,169], DecoderTrap::Strict).is_err());
assert_eq!(ISO_8859_6.decode(&[65,99,109,101,169], DecoderTrap::Replace),
           Ok("Acme\u{fffd}".to_string()));
assert_eq!(ISO_8859_6.decode(&[65,99,109,101,169], DecoderTrap::Ignore),
           Ok("Acme".to_string()));

将输入编码或解码到已分配的缓冲区中

use encoding::{Encoding, EncoderTrap, DecoderTrap};
use encoding::all::{ISO_8859_2, ISO_8859_6};

let mut bytes = Vec::new();
let mut chars = String::new();

assert!(ISO_8859_2.encode_to("Acme\u{a9}", EncoderTrap::Ignore, &mut bytes).is_ok());
assert!(ISO_8859_6.decode_to(&[65,99,109,101,169], DecoderTrap::Replace, &mut chars).is_ok());

assert_eq!(bytes, [65,99,109,101]);
assert_eq!(chars, "Acme\u{fffd}");

自定义编码器陷阱的实用示例

use encoding::{Encoding, ByteWriter, EncoderTrap, DecoderTrap};
use encoding::types::RawEncoder;
use encoding::all::ASCII;

// hexadecimal numeric character reference replacement
fn hex_ncr_escape(_encoder: &mut RawEncoder, input: &str, output: &mut ByteWriter) -> bool {
    let escapes: Vec<String> =
        input.chars().map(|ch| format!("&#x{:x};", ch as isize)).collect();
    let escapes = escapes.concat();
    output.write_bytes(escapes.as_bytes());
    true
}
static HEX_NCR_ESCAPE: EncoderTrap = EncoderTrap::Call(hex_ncr_escape);

let orig = "Hello, 世界!".to_string();
let encoded = ASCII.encode(&orig, HEX_NCR_ESCAPE).unwrap();
assert_eq!(ASCII.decode(&encoded, DecoderTrap::Strict),
           Ok("Hello, &#x4e16;&#x754c;!".to_string()));

根据WHATWG编码标准从字符串标签获取编码

use encoding::{Encoding, DecoderTrap};
use encoding::label::encoding_from_whatwg_label;
use encoding::all::WINDOWS_949;

let euckr = encoding_from_whatwg_label("euc-kr").unwrap();
assert_eq!(euckr.name(), "windows-949");
assert_eq!(euckr.whatwg_name(), Some("euc-kr")); // for the sake of compatibility
let broken = &[0xbf, 0xec, 0xbf, 0xcd, 0xff, 0xbe, 0xd3];
assert_eq!(euckr.decode(broken, DecoderTrap::Replace),
           Ok("\u{c6b0}\u{c640}\u{fffd}\u{c559}".to_string()));

// corresponding Encoding native API:
assert_eq!(WINDOWS_949.decode(broken, DecoderTrap::Replace),
           Ok("\u{c6b0}\u{c640}\u{fffd}\u{c559}".to_string()));

类型和其他内容

Encoding有三个主要入口点。

编码 是一种单字符编码。它包含 encodedecode 方法,用于将 String 转换为 Vec<u8> 以及反向转换。对于错误处理,它们分别接收 陷阱EncoderTrapDecoderTrap),将任何错误替换为某些字符串(例如 U+FFFD)或序列(例如 ?)。您还可以使用 EncoderTrap::StrictDecoderTrap::Strict 陷阱在错误时停止。

获取 编码 有两种方式

  • encoding::all 为每种支持的编码提供了静态项。当编码不会改变或只需要少数几种时,应使用它们。结合链接时间优化,任何未使用的编码都会从二进制文件中删除。
  • encoding::label 提供了从给定字符串(“标签”)动态获取编码的功能。它们将返回对编码的静态引用,其类型也称为 EncodingRef。当事先不知道所需编码列表时,这很有用,但它会导致二进制文件更大,并错过优化机会。

RawEncoder 是一个实验性的增量编码器。在 raw_feed 的每个步骤中,它接收一个字符串切片,并将任何编码字节输出到一个通用的 ByteWriter(通常是 Vec<u8>)。如果发生任何错误,它将在第一个错误处停止,并返回一个 CodecError 结构体。调用者负责在编码过程结束时调用 raw_finish

RawDecoder 是一个实验性的增量解码器。在 raw_feed 的每个步骤中,它接收一个字节序列切片,并将任何解码字符输出到一个通用的 StringWriter(通常是 String)。否则它与 RawEncoder 相同。

应首选 Encoding::{encode,decode} 作为主要接口。 RawEncoderRawDecoder 是实验性的,可能会发生重大变化。有关更多信息,请参阅 encoding::types 模块中的附加文档。

支持的编码

编码涵盖了 WHATWG 编码标准中指定的所有编码以及更多

  • 7位严格ASCII (ascii)
  • UTF-8 (utf-8)
  • 小端 UTF-16 (utf-16utf-16le) 和大端 UTF-16 (utf-16be)
  • WHATWG 编码标准中所有的单字节编码
    • IBM 编码页 866
    • ISO 8859-{2,3,4,5,6,7,8,10,13,14,15,16}
    • KOI8-R, KOI8-U
    • MacRoman (macintosh),Macintosh 西里尔编码 (x-mac-cyrillic)
    • Windows 编码页 874, 1250, 1251, 1252(代替 ISO 8859-1),1253,1254(代替 ISO 8859-9),1255,1256,1257,1258
  • WHATWG 编码标准中所有的多字节编码
    • Windows代码页949(euc-kr,因为严格的EUC-KR几乎不用)
    • EUC-JP和Windows代码页932(shift_jis,因为它是Shift_JIS最广泛的应用扩展)
    • ISO-2022-JP,具有非对称JIS X 0212支持(注意:这尚未达到当前标准)
    • GBK
    • GB 18030
    • Big5-2003,带有HKSCS-2008扩展
  • 最初由WHATWG编码标准指定的编码
    • HZ
  • ISO 8859-1(与Windows代码页1252不同)

括号内的名称是指由WHATWG编码标准分配的编码的主要名称。

许多传统的字符编码缺乏适当的规范,甚至有规范的那些也非常依赖于实际的实现。因此,在选择所需的字符编码时应谨慎。在这方面唯一可靠的规范是WHATWG编码标准和Unicode联盟提供的供应商映射。如有疑问,请查看源代码和规范以获取详细说明。

依赖项