C 字符串字面量
总结
- 形式为
c"foo"
或cr"foo"
的字面量表示类型为&core::ffi::CStr
的字符串。
详情
从 Rust 1.77 开始,可以使用带有 c
或 cr
前缀的 C 字符串字面量语法编写 C 字符串。
以前,要生成一个有效的字符串字面量,使其能够与以 NUL 字节结尾的 C API 进行互操作,是一项具有挑战性的任务。cstr
crate 是一个流行的解决方案,但它需要编译一个开销相当大的过程宏。现在,可以使用字面量语法符号直接编写 C 字符串,这将生成一个类型为 &core::ffi::CStr
的值,该值会自动以 NUL 字节结尾。
#![allow(unused)] fn main() { use core::ffi::CStr; assert_eq!(c"hello", CStr::from_bytes_with_nul(b"hello\0").unwrap()); assert_eq!( c"byte escapes \xff work", CStr::from_bytes_with_nul(b"byte escapes \xff work\0").unwrap() ); assert_eq!( c"unicode escapes \u{00E6} work", CStr::from_bytes_with_nul(b"unicode escapes \xc3\xa6 work\0").unwrap() ); assert_eq!( c"unicode characters αβγ encoded as UTF-8", CStr::from_bytes_with_nul( b"unicode characters \xce\xb1\xce\xb2\xce\xb3 encoded as UTF-8\0" ) .unwrap() ); assert_eq!( c"strings can continue \ on multiple lines", CStr::from_bytes_with_nul(b"strings can continue on multiple lines\0").unwrap() ); }
C 字符串不允许内部出现 NUL 字节(例如使用 \0
转义字符)。
与常规字符串类似,C 字符串也支持带有 cr
前缀的“原始”语法。这些原始 C 字符串不会处理反斜杠转义,这使得编写包含反斜杠的字符串变得更容易。可以通过用 #
字符包围引号来包含双引号。可以使用多个 #
字符来避免与内部 "#
序列产生歧义。
#![allow(unused)] fn main() { assert_eq!(cr"foo", c"foo"); // Number signs can be used to embed interior double quotes. assert_eq!(cr#""foo""#, c"\"foo\""); // This requires two #. assert_eq!(cr##""foo"#"##, c"\"foo\"#"); // Escapes are not processed. assert_eq!(cr"C:\foo", c"C:\\foo"); }
有关更多详细信息,请参阅参考。
迁移
只有在宏可能假设存在类似于 c"…"
或 cr"…"
的标记序列时,才需要进行迁移。在 2021 版本之前,这些标记会被标记为两个单独的标记,但在 2021 版本中,它们会显示为单个标记。
作为 2021 版本语法保留的一部分,任何可能遇到此问题的宏输入都应该发出来自 rust_2021_prefixes_incompatible_syntax
迁移 linter 的警告。有关更多详细信息,请参阅该章节。