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

如何正确地将十六进制转义添加到字符串文字中?

c99 c
  •  60
  • unalignedmemoryaccess  · 技术社区  · 7 年前

    char str[] = "abcde"; // 'a', 'b', 'c', 'd', 'e', 0x00
    char str2[] = "abc\x12\x34"; // 'a', 'b', 'c', 0x12, 0x34, 0x00
    

    这两个示例的内存中都有6个字节。现在,如果你想增加价值,问题就存在了 [a-fA-F0-9] 十六进制输入后。

    //I want: 'a', 'b', 'c', 0x12, 'e', 0x00
    //Error, hex is too big because last e is treated as part of hex thus becoming 0x12e
    char problem[] = "abc\x12e";
    

    //This will work, bad idea
    char solution[6] = "abcde";
    solution[3] = 0x12;
    

    这可以奏效,但如果你把它当作 const

    //This will not work
    const char solution[6] = "abcde";
    solution[3] = 0x12; //Compilation error!
    

    如何正确插入 e \x12 没有触发错误?


    UTF-8 字符串作为常量,如果字符的十六进制值大于ASCII表所能容纳的值,则必须使用十六进制值。

    3 回复  |  直到 7 年前
        1
  •  68
  •   user694733    7 年前

    使用3个八进制数字:

    char problem[] = "abc\022e";
    

    char problem[] = "abc\x12" "e";
    

    • 与十六进制转义不同,标准定义了三位数字作为八进制转义的最大值。

      6.4.4.4字符常数

      ...

      octal-escape-sequence:
          \ octal-digit
          \ octal-digit octal-digit
          \ octal-digit octal-digit octal-digit
      

      hexadecimal-escape-sequence:
          \x hexadecimal-digit
          hexadecimal-escape-sequence hexadecimal-digit
      
    • 5.1.1.2翻译阶段

      ...

      1. 字符串文字被转换为执行字符的相应成员 设置如果没有对应的成员,则将其转换为实现- 非空(宽)字符的已定义成员。8)

      2. 连接相邻的字符串文字标记。

        2
  •  25
  •   Community raghavsood33    4 年前

    之后 对于转义字符转换,您可以只使用:

    char problem[] = "abc\x12" "e";
    

    尽管为了可读性,您可能更喜欢完全分离:

    char problem[] = "abc" "\x12" "e";
    

    对于我们当中的语言律师来说,这包括在 C11 5.1.1.2 Translation phases

    1. 字符串 转换为执行字符集的相应成员;如果没有对应的成员,则将其转换为除空(宽)字符以外的实现定义的成员。

    2. 连接相邻的字符串文字标记。

        3
  •  5
  •   Damon    7 年前

    我为什么这么问?当您想将UTF-8字符串构建为常量时,必须使用字符的十六进制值大于ASCII表所能容纳的值。

    不得不 。从C11开始,您可以使用 u8

    char solution[] = u8"no need to use hex-codes á駵";
    

    (顺便说一句,C++11也支持同样的功能)