在数组中设置 NULL 的奇怪行为
Strange behavior by setting NULL in array
当我尝试在 c 中的字符串数组(char 数组)的末尾设置 NULL 值时,我有一个奇怪的行为。我需要将参数传递给带有 execv 的进程,并且我的所有参数都是 int 类型,所以我试图获取一个字符串数组,所有参数都转换为 char 数组。我创建了一个 returns 这个字符串数组的函数,但是当我将数组的最后一个值设置为 NULL(在参数中有一个终止值)时,我丢失了存储在第二个位置的值。如果我删除 NULL 值,则不会发生任何问题。这是代码,希望有人能帮助我
char **getParams(int offset, short isNode, int first) {
printf("Get params\n");
int args = 8;
int totalSize = 0;
int tmp[args];
tmp[0] = sizeof(char) * 5; // user / node
tmp[1] = snprintf(NULL, 0, "%d", x);
tmp[2] = snprintf(NULL, 0, "%d", x2);
tmp[3] = snprintf(NULL, 0, "%d", x3);
tmp[4] = snprintf(NULL, 0, "%d", x4);
tmp[5] = snprintf(NULL, 0, "%d", x5);
tmp[6] = snprintf(NULL, 0, "%d", x6);
tmp[7] = snprintf(NULL, 0, "%d", x7);
int i = 0;
for (i = 0; i < args; i++) totalSize += tmp[i];
char **_pars = malloc(totalSize + sizeof(NULL));
i = 0;
for (i = 0; i < args; i++) _pars[i] = malloc(tmp[i]);
_pars[0] = isNode == 1 ? "aaaa" : "bbbb" ;
sprintf(_pars[1], "%d", x);
sprintf(_pars[2], "%d", x2);
sprintf(_pars[3], "%d", x3);
sprintf(_pars[4], "%d", x4);
sprintf(_pars[5], "%d", x5);
sprintf(_pars[6], "%d", x6);
sprintf(_pars[7], "%d", x7);
printf("Value: %s", _pars[1]); /// Print without problem value
_pars[8] = NULL; //// ,--- Here happens the issue
printf("Value: %s", _pars[1]); /// Doesnt print any value
return _pars;
}
我也试过把它放在我 malloc 数组位置的 for 之后,但没有结果
_pars[8] = malloc(sizeof(NULL));
_pars
被假定为指向 char 的指针数组,这意味着
_pars = malloc(args * sizeof(char*));
但是你为字符串分配了内存,指针应该指向。
你所有的分配都是错误的。
首先你要创建一个包含8
个元素的数组,所以第一个分配应该是
char **_pars = malloc(8 * sizeof *_pars);
或者,如果您希望数组由空指针终止,您需要分配 9
个元素(将 8
换成上面的 9
)。
其次,snprintf
返回的大小 不 包含空终止符,因此您的所有调用
_pars[i] = malloc(tmp[i]);
应该是
_pars[i] = malloc(tmp[i] + 1);
以适应空终止符。
另一方面,如果将所有 x
值放在一个数组中,则所有代码都可以大大简化:
int exes[8] = { x, x2, x3, x4, x5, x6, x7 };
因为这样你就可以对所有重复代码使用循环:
for (unsigned i = 1; i < 8; ++i)
{
tmp[i] = snprintf(NULL, 0, "%d", exes[i]);
}
当我尝试在 c 中的字符串数组(char 数组)的末尾设置 NULL 值时,我有一个奇怪的行为。我需要将参数传递给带有 execv 的进程,并且我的所有参数都是 int 类型,所以我试图获取一个字符串数组,所有参数都转换为 char 数组。我创建了一个 returns 这个字符串数组的函数,但是当我将数组的最后一个值设置为 NULL(在参数中有一个终止值)时,我丢失了存储在第二个位置的值。如果我删除 NULL 值,则不会发生任何问题。这是代码,希望有人能帮助我
char **getParams(int offset, short isNode, int first) {
printf("Get params\n");
int args = 8;
int totalSize = 0;
int tmp[args];
tmp[0] = sizeof(char) * 5; // user / node
tmp[1] = snprintf(NULL, 0, "%d", x);
tmp[2] = snprintf(NULL, 0, "%d", x2);
tmp[3] = snprintf(NULL, 0, "%d", x3);
tmp[4] = snprintf(NULL, 0, "%d", x4);
tmp[5] = snprintf(NULL, 0, "%d", x5);
tmp[6] = snprintf(NULL, 0, "%d", x6);
tmp[7] = snprintf(NULL, 0, "%d", x7);
int i = 0;
for (i = 0; i < args; i++) totalSize += tmp[i];
char **_pars = malloc(totalSize + sizeof(NULL));
i = 0;
for (i = 0; i < args; i++) _pars[i] = malloc(tmp[i]);
_pars[0] = isNode == 1 ? "aaaa" : "bbbb" ;
sprintf(_pars[1], "%d", x);
sprintf(_pars[2], "%d", x2);
sprintf(_pars[3], "%d", x3);
sprintf(_pars[4], "%d", x4);
sprintf(_pars[5], "%d", x5);
sprintf(_pars[6], "%d", x6);
sprintf(_pars[7], "%d", x7);
printf("Value: %s", _pars[1]); /// Print without problem value
_pars[8] = NULL; //// ,--- Here happens the issue
printf("Value: %s", _pars[1]); /// Doesnt print any value
return _pars;
}
我也试过把它放在我 malloc 数组位置的 for 之后,但没有结果
_pars[8] = malloc(sizeof(NULL));
_pars
被假定为指向 char 的指针数组,这意味着
_pars = malloc(args * sizeof(char*));
但是你为字符串分配了内存,指针应该指向。
你所有的分配都是错误的。
首先你要创建一个包含8
个元素的数组,所以第一个分配应该是
char **_pars = malloc(8 * sizeof *_pars);
或者,如果您希望数组由空指针终止,您需要分配 9
个元素(将 8
换成上面的 9
)。
其次,snprintf
返回的大小 不 包含空终止符,因此您的所有调用
_pars[i] = malloc(tmp[i]);
应该是
_pars[i] = malloc(tmp[i] + 1);
以适应空终止符。
另一方面,如果将所有 x
值放在一个数组中,则所有代码都可以大大简化:
int exes[8] = { x, x2, x3, x4, x5, x6, x7 };
因为这样你就可以对所有重复代码使用循环:
for (unsigned i = 1; i < 8; ++i)
{
tmp[i] = snprintf(NULL, 0, "%d", exes[i]);
}