- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
使用 C 几周后,我现在讨厌它。
我现在尝试使用 execl 将参数传递给另一个程序,并且参数的格式会发生奇怪的事情:
int select[2], result[2];
char str_w,str_r;
snprintf(&str_w, 2, "%d", select[1]);
snprintf(&str_r, 2, "%d", result[0]);
printf("%d %d %s %s\n", select[1], result[0], &str_w, &str_r);
execl("./recive.x","./recive.x",&str_w,&str_r,(char *)NULL);
这里重要的是 snprintf:我正在尝试将 vector 中的数字转换为字符串。该数字将小于 10。当我执行此操作时,显示的 printf 的结果是:
5 6 6
这意味着 select[1] 中有一个数字 (5),result[0] 中有一个数字 (6),并且 result[0] 已正确转换为字符串,但 select[1] 没有。
这到底是什么行为!!
提前谢谢您!
最佳答案
After a few weeks playing with C, I now hate it.
这种 react 并不罕见。我的 CS 入门课有三分之一换了专业,理由是 C 语言有困难(这是一种糟糕的教学语言)。我花了好几年的时间才充分理解它,但一旦我明白了,我就开始欣赏它。
char str_w,str_r;
snprintf(&str_w, 2, "%d", select[1]);
snprintf(&str_r, 2, "%d", result[0]);
这是你的主要问题; str_w
和 str_r
仅足以容纳单个 char
值,而不是字符串(这需要至少 2 个字符)。相反,您需要将 str_w
和 str_r
声明为 char
的数组,足够大以容纳 的字符串表示形式您期望的最大 int
,加上符号空格(如果值为负),加上 0 终止符。例如,如果您没有限制 select
或 result
上的值:
#define MAX_DIGITS 20 // max decimal digits for 64-bit integer
#define SIZE MAX_DIGITS+2 // 2 extra for sign and 0 terminator
char str_w[SIZE], str_r[SIZE];
sprintf(str_w, "%d", select[1]);
sprintf(str_r, "%d", result[0]);
通过使目标数组足够大以容纳任何可能的输入,您不必担心溢出。是的,您会遇到一些内部碎片,并且根据您的应用程序,这可能会或可能不会成为问题。但我只是喜欢让事情变得简单。
如果您知道一个事实,您的 select
和 result
数组永远不会保存 0..10 范围之外的值,那么您可以将 SIZE 设置为 3(最多 2 位数字加 0 终止符)。
Which means that there's a number (5) in select[1], there's a number (6) in result[0] and result[0] is converted to string properly but select[1] no.
What the hell is that behaviour!!
由于您向缓冲区传递的地址不足以容纳结果,因此行为未定义,这意味着编译器没有义务警告您正在执行某些操作危险的。
这是最有可能发生的情况(由于行为未定义,任何事件序列都是可能的,但我认为这是对结果的合理解释)。首先,假设您的变量在内存中的布局如下:
Item Address Value
---- ------- -----
str_r 0xffec1230 ??
str_w 0xffec1231 ??
0xffec1232 ??
str_w
和str_r
分配给连续的字节,并且它们的初始值是不确定的。在第一个 snprintf
到 str_w
之后,您的内存现在如下所示:
Item Address Value
---- ------- -----
str_r 0xffec1230 ??
str_w 0xffec1231 '5'
0xffec1232 0
snprintf
会将尾随 0 终止符写入缓冲区;在这种情况下,它将终止符写入 str_w
后面的字节。在第二次 sprintf 调用之后,内存现在如下所示:
Item Address Value
---- ------- -----
str_r 0xffec1230 '6'
str_w 0xffec1231 0
0xffec1232 0
第二个 snprintf
调用将 0 终止符写入 str_r
之后的字节,而该字节恰好是 str_w
;您最终会破坏之前写入其中的值。这就是为什么您看到 str_r
字符串而不是 str_w
字符串。
关于c - snprintf c 的奇怪行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14922004/
在我从事的项目(一个 Windows 和 Ubuntu 应用程序)中,我定义了一个与日志库交互的宏。本质上,这个宏接受类似 printf 的输入,转换为字符串,并将其发送到日志库。我附上一个使用 st
我正在尝试使用 snprintf基于我读过的手册的函数是 的一部分header 但是我收到一个错误,它已被隐式声明。这是我的代码: #include #include #include str
当我通过 Fortify 分析器工具之一运行我的代码时,它提示 snprintf 说“格式字符串参数没有正确限制函数可以写入的数据量” 我了解 snprintf 不应导致缓冲区溢出。但仍然是为什么该工
在我的代码中,我使用 snprintf 如下所示,并且能够看到以下行为 char text[30] = {0}; snprintf(text, sizeof(text), "%s", "hello")
我创建了以下程序: #include #include #define TESTER "name=%s " int main(){ char *x; x = malloc(100);
当我通过 Fortify 分析器工具之一运行我的代码时,它提示 snprintf 说“格式字符串参数没有正确限制函数可以写入的数据量” 我了解 snprintf 不应导致缓冲区溢出。但仍然是为什么该工
我收到 format not a string literal and no format arguments当我在 Linux 上编译它时发出警告。 snprintf显示 const char*对于
char symbols[16] = ""; int index = 0; while (1) { if (index % 2) snprintf(symbols, siz
我正在尝试了解 snprintf 并找到了 this answer举个例子: char buf[20] = ""; char *cur = buf, * const end = buf + sizeo
已关闭。此问题需要 debugging details 。目前不接受答案。 编辑问题以包含 desired behavior, a specific problem or error, and the
我正在尝试理解 C 中的 char 指针。基本上我正在做的是声明一个 char* 指针 main 并在另一个函数中通过引用传递并在那里进行修改。现在,我想打印 main 中 char 的值,这给了我段
我正在使用 C 语言(指针、指针-指针等,我喜欢它)做我的第一步,所以如果这是一个愚蠢的问题,请仁慈。 该片段不输出任何内容: char buf[256]; snprintf(buf, sizeof
我需要将一些数字(整数和 double )转换为 std::strings,并且出于性能原因不能使用 stringstream(我们发现它在同时使用时非常慢) 如果能做这样的事情就好了 templat
我已经查看这段代码一段时间了,但似乎找不到我的错误。我想我知道 snprintf(dest, n, fmt, src) 应该如何工作(它在填充 后返回 src 缓冲区中剩余的字符数>dest 缓冲区与
为什么 snprintf 在第二种情况下给出不同的值。是不是因为任何整数限制。您能否解释一下 snprintf 的工作原理以及为什么会出现负值 #include #include main() {
考虑以下代码: char *myContent = "content"; int size = snprintf(NULL, 0, "INSERT INTO myTable (col1) VALUES
我正在编写自己的 ncurses 库,突然发现在 GDB 中 snprintf() 返回的长度大于我指定的长度。这是定义的行为还是我的一些错误? (可重现的)片段代码是这样的: niko: snipp
我写了一个简单的小程序来使用 snprintf 读取具有以下格式的文件, skip first 15 chars , next 9 chars are sequence number, next 2
我使用snprintf 将格式化的数据写入磁盘,但我有一个问题,如何将它保存到用户的主目录? snprintf(filename, sizeof(filename), "%s_%s.sho", cl
定义: CHAR_BACKSLASH 定义为 '\\' 或 0x5C 变量: workingDir 是一个 C 字符串 myFilePath 是一个 C 字符串 int len = strlen(wo
我是一名优秀的程序员,十分优秀!