如何putchar()
仅在 的帮助下打印整数。我想在不使用外部存储的情况下做到这一点。
这个问题在去年的一次采访中被问到。
5 回答
当面对面试的模糊要求时,表达你的假设是个好主意。
我认为只能使用的putchar
要求意味着它是我被允许调用的唯一库函数。我还假设“没有外部存储”意味着我无法显式创建缓冲区。如果面试官同意我的假设,我会继续:
void pr_int(int n) {
if (n < 0) {
putchar('-');
n = -n;
}
if (n / 10 != 0)
pr_int(n / 10);
putchar((n % 10) + '0');
}
如果面试官随后评论说这n = -n;
将失败INT_MIN
,如下所述,那么我会将其重写为:
void pr_uint(unsigned int n) {
if (n / 10 != 0)
pr_uint(n / 10);
putchar((n % 10) + '0');
}
void pr_int(int n) {
if (n < 0) {
putchar('-');
n = -n;
}
pr_uint((unsigned int) n);
}
正确回答这个问题很大程度上取决于“外部存储”和“putchar
仅”的含义。
void print_int_r (int x, int neg) {
int y = x/10;
int d = x%10;
if (y) print_int_r(y, neg);
putchar('0' + (neg ? -d : d));
}
void print_int (int x) {
int neg = x < 0;
if (neg) putchar('-');
print_int_r(x, neg);
putchar('\n');
}
上述实现假定 C99 语义,如 C99 第 6.5.5 p6 节所述:
当整数被除法时,
/
运算符的结果是代数商,其中任何小数部分被丢弃。如果商a/b
是可表示的,则表达式(a/b)*b + a%b
应等于a
。
但是,ANSI C (C 89) 的语义%
更差。ANSI C 第 3.3.5 p5 节说:
如果任一操作数为负,则
/
运算符的结果是小于代数商的最大整数还是大于代数商的最小整数是实现定义的,%
运算符结果的符号也是如此。
费鲁乔的第二个答案几乎是完美的。问题是转换不正确。n = -n
如果操作的结果是一个不能用 表示的值,则 的结果是未定义的int
。因此,转换应该以这种方式完成:
void pr_int(int n) {
if (n < 0) {
putchar('-');
pr_uint(-(unsigned int)n);
} else
pr_uint(n);
putchar('\n');
}
该解决方案现在符合所有 ISO C 标准。详细信息可以在这里找到。
考虑使用 itoa 函数(您需要导入它的库),然后循环遍历它生成的 cstring 中的每个字符(使用 strlen 获取此循环的上限),然后简单地对每个字符使用 putchar()。
我刚刚组装了一些可怕的东西。它主要是概念验证,真的很可怕,仅适用于正整数,但几乎不使用存储空间。啊,整数也不能太大,而且可能有问题。
#include <stdio.h>
#include <assert.h>
int main()
{
const int max_precision = 100000;
int b = 7414;
int max = b * max_precision;
assert(b > 0);
while (b <= max && b >= 0)
{
putchar('0' + (b / max_precision) % 10);
b *= 10;
}
putchar('\n');
}
max_precision
设置将打印多少位数。b
存储实际数字,并max
用于终止循环(该循环或整数溢出)。