1
options->dict_size = UINT32_C(1) << (uint8_t []){
        18, 20, 21, 22, 22, 23, 23, 24, 25, 26 }[level];

http://svn.r-project.org/R/trunk/src/extra/xz/lzma/lzma_encoder_presets.c

#ifndef UINT32_C
#   if UINT_MAX != 4294967295U
#       error UINT32_C is not defined and unsigned int is not 32-bit.
#   endif
#   define UINT32_C(n) n ## U
#endif

为windows编译这个。但是出现语法错误

error C2059: syntax error : '{'

error C2143: syntax error : missing ';' before '{'

error C2337: 'level' : attribute not found

typedef struct {
    uint32_t dict_size;
    // ...
} lzma_options_lzma;

有没有人试过这个?

另外,我从未见过像这样的代码uint8_t []{...}[level]

这是什么意思?

4

2 回答 2

5
const static uint8_t shift_lookup[] = {
    18, 20, 21, 22, 22, 23, 23, 24, 25, 26 };
options->dict_size = UINT32_C(1) << shift_lookup[level];

shift_lookup代码中尚未使用的名称在哪里。

(uint8_t []){...}是 C99 复合文字,它是数组类型的未命名对象。MSVC 没有实现 C99。要在 C89 中获得等价物,您必须为其命名。

(uint8_t []){...}[level]是数组的普通索引运算符,应用于文字。

对于这种特殊情况,数组恰好是字符类型,C89 实际上已经有一种可以工作的文字:字符串文字。

options->dict_size = UINT32_C(1) << "\x12\x14\x15\x16\x16\x17\x17\x18\x19\x1a"[level];

不过我不推荐它。

于 2013-03-07T10:26:09.617 回答
4

那是一个C99 复合文字

它定义了一个数组,然后在同一个表达式中对数组进行索引。如果level是 0,它将移动 18 位,如果它是 1,它将移动 20 位,依此类推。

如果您尝试使用 Visual Studio 构建它,那就是您的问题,因为 Visual Studio 不支持 C99。

修复它需要重构以删除内联数组,并将其改为常规数组。

于 2013-03-07T08:38:46.697 回答