我想使用strtok将路径名称分成序列。但是我提出了一个问题,我的代码如下所示:
int main(void)
{
char test[] = "/hoe/wahoo/Documents/hello/test";
char *str[8];
int index = 0;
int count = 0;
str[index] = strtok(test, "\\/");
while (str[index] && *str[index]) {
index++;
str[index] = strtok(NULL, "\\/");
}
for (index=0; index<8; index++) {
if (str[index] && *str[index]) {
count++;
}
}
printf("%d\n", count);
return 0;
}
显然,我收到错误segmentation error
,我知道错误的来源。一次,我将第5行中的int index = 0;
更改为static index = 0;
。我发现它确实有用!!
为什么?似乎我将数组的索引更改为静态,即数组将是静态的。
答案 0 :(得分:4)
在第一个循环中,您仔细检查非空ptr:
str[index] = strtok(test, "\\/");
while (str[index] && *str[index]) {
index++;
str[index] = strtok(NULL, "\\/");
}
但是在你的第二个循环中你没有,并且你没有初始化str
来获得值,这会引入未定义的行为。这就是为什么当你改变一些其他变量时,例如通过将一个变为静态变量,会发生不同的行为。
for (index=0; index<8; index++) {
if (str[index] && *str[index]) {
count++;
}
}
这个循环需要是:
for (index = 0; str[index] && *str[index]; ++index) {
++count;
或者更好的是,你可以把整个写成
int main(void)
{
char test[] = "/hoe/wahoo/Documents/hello/test";
char *str[8] = { NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL };
int count = 0;
str[count] = strtok(test, "\\/");
while (str[count] && *str[count]) {
str[++count] = strtok(NULL, "\\/");
}
printf("%d\n", count);
}
---编辑---
另请注意,strtok
会修改原始字符串。完成循环后,test
中的路径separtors将替换为'\ 0'。
答案 1 :(得分:3)
这与静态变量无关。您只需要初始化 echo "<div class='shoe-view'>";
echo "<img class='show-view-image' src='scripts/shoes/uploads/".$result["imagename"]."' alt='".$result["imagename"]."'/>";
echo "<p class='sub-heading desc catalogfont' style='color:rgb(184, 55, 60);'>".$result["shoename"]."</p>";
echo "<p class='content catalogfont' style='font-weight:bold;'>".$result["price"]."</p>";
echo "<p class='content catalogfont' style='font-weight:bold;'>".$result["Color"]." : ".$result["brand"]."</p>";
echo "<form action='buyshoe.php' method='post'>";
echo "<button value='".$result["id"]."' name='messagebutton' class='send-message'>Buy Shoe</button>";
echo "</form>";
echo "</div>";
,否则未使用的元素将包含随机垃圾,您将获得未定义的行为(很可能是因为您尝试迭代超出数组的末尾)。
请注意,未定义的行为是未定义的行为 - 当您执行此类操作时,字面上会出现任何。对代码中不相关区域的随机更改可能会影响观察到的结果,但这实际上只是一种分心,并没有解决潜在的问题。
所以改变:
str[]
为:
char *str[8];
一切都会好的。
答案 2 :(得分:0)
你已经得到了一个很好的答案。
这是另一段代码:
#include <string.h>
#include <stdio.h>
int main()
{
char test[] = "/hoe/wahoo/Documents/hello/test";
char delims[] = "\\/";
char *str[8];
int count = 0;
str[0] = strtok(test, delims);
while (str[count]) {
printf("%s,", str[count]);
count++;
str[count] = strtok(NULL, delims);
}
printf("\n%d\n", count);
return 0;
}
输出:
hoe,wahoo,Documents,hello,test,
5
请注意:这是可读的,但效率很低,因为它使用索引来处理str中的元素。
以下是我要编写的内容(指针为您提供优势):
int main()
{
char test[] = "/hoe/wahoo/Documents/hello/test";
char delims[] = "\\/";
char *str[8];
char **p = str;
int count = 0;
*p = strtok(test, delims);
while (*p) {
printf("%s,", *p);
count++;
*(++p) = strtok(NULL, delims);
}
printf("\n%d\n", count);
return 0;
}
注意:上面的所有代码都没有检查达到的最大令牌数。我建议将其添加以避免出现段错/不可预测的行为。