有一天,我想在C中将整数转换为char *,这个int可以是负数。
我也无法使用 sprintf 、snprintf ,那么我该怎么做?
最佳答案
自己动手itoa()
类似的函数,第一个必须解决如何处理内存。最简单的方法是为所有可能的情况使用足够大的内存 int
值(INT_MIN
)。
缓冲区所需大小在数学上为 ceiling(log10(-INT_MIN))+3
。这可以近似为:
#include <limits.h>
#define INT_STR_SIZE (sizeof(int)*CHAR_BIT/3 + 3)
然后使用 %10
从最低有效数字开始逐一构建数字然后/10
减少该值。
通过使用 do
循环,代码捕获 x==0
的极端情况因为至少有一位数字。
此代码避免 if (x < 0) { x = -x; ...
作为否定INT_MIN
(或者乘以 -1 会导致 int
溢出,即 UB。
#include <limits.h>
#define INT_STR_SIZE (sizeof(int)*CHAR_BIT/3 + 3)
char *my_itoa(char *dest, size_t size, int x) {
char buf[INT_STR_SIZE];
char *p = &buf[INT_STR_SIZE - 1];
*p = '\0';
int i = x;
do {
*(--p) = abs(i%10) + '0';
i /= 10;
} while (i);
if (x < 0) {
*(--p) = '-';
}
size_t len = (size_t) (&buf[INT_STR_SIZE] - p);
if (len > size) {
return NULL; // Not enough room
}
return memcpy(dest, p, len);
}
使用 C99 或更高版本,代码可以使用复合文字来处理缓冲区创建,允许每个 mt_itoa()
有单独的缓冲区打电话。
// compound literal C99 or later
#define MY_ITOA(x) my_itoa((char [INT_STR_SIZE]){""}, INT_STR_SIZE, x)
int main(void) {
printf("%s %s %s %s\n", MY_ITOA(INT_MIN), MY_ITOA(-1), MY_ITOA(0), MY_ITOA(INT_MAX));
return (0);
}
输出
-2147483648 -1 0 2147483647
关于c - 如何在C中将int转换为char*(不使用sprintf),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36380105/