c-size_t,用作公式中的值

  • 本文关键字:c-size c size-t
  • 更新时间 :
  • 英文 :


下面是一个读取行的函数的简短片段。它怎么可能将bufsize((size_t)-1)/2进行比较?

我想象着将一个变量与例如int进行比较——这是不可能的;相反,我认为INT_MAX是正确的。那么,这些代码如何才能真正工作并且不出错呢?

int c;
size_t bufsize = 0;
size_t size = 0;
while((c=fgetc(infile)) != EOF) {
    if (size >= bufsize) {
        if (bufsize == 0)
                bufsize = 2;
        else if (bufsize <= ((size_t)-1)/2)
                bufsize = 2*size;
        else {
                free(line);
                exit(3);
        }
        newbuf = realloc(line,bufsize);
        if (!newbuf) {
                free(line);
                abort();
        }
        line = newbuf;
    }
    /* some other operations */
}
(size_t)-1

这是将值-1强制转换为size_t(type)value是C

由于size_t是一个无符号类型,这实际上是size_t可以保持的最大值,因此它用于确保缓冲区大小实际上可以安全地加倍(因此随后可以除以2)。

该代码依赖于一些关于比特的假设,然后进行众所周知的破解来找到最大size_t值(前提是size_t不能容纳比寄存器更多的比特,这在许多机器上是安全的)。

首先,它用1位填充寄存器,然后将其强制转换为size_t数据类型,这样比较就可以工作了。只要该寄存器的位数大于size_t数据类型,则未使用的1位(如果有)将被截断,您将获得可容纳size_t位的最大无符号数。

之后,它除以2得到该数字的一半,并进行比较,看看在不超过"最大"size_t的情况下增加大小是否安全。但到那时,它将划分一个size_t数据类型,并比较两个size_t数据类型(类型安全操作)。

如果你真的想去掉这个小魔法(好吧,这不是我见过的最糟糕的小魔法例子)。考虑以下片段

    else if (bufsize <= ((size_t)-1)/2)
            bufsize = 2*size;

可以用代替

    else if (bufsize <= (MAX_SIZE/2)
            bufsize = 2*size;

并且是类型安全的而不进行强制转换并且更可读。

(size_t)-1-1强制转换为类型size_t,从而产生SIZE_MAX(在stdint.h中定义的宏),这是size_t类型可以容纳的最大值。

因此,比较是检查bufsize是否小于或等于size_t 中可包含的最大值的一半

size_t没有被解释为一个值,它被用来将负1的值强制转换为size_t类型。

((size_t)-1)/2

是将-1强制转换为size_t,然后除以2。

((size_t)-1)/2)中的size_t只是用作强制转换:将-1强制转换为size_t

这里的技巧size_t是无符号的,因此转换后的(size_t) -1将转换为size_tSIZE_MAX的最大值。这在循环的上下文中很有用。然而,我更希望看到SIZE_MAX直接使用,而不是这个技巧。

相关内容

  • 没有找到相关文章

最新更新