C-strcpy()处的分段故障 #包括 #包括 #包括 char*vStrs[]={“Max”、“Moritz”、“Bolte”、“Hans Huckebein”、“Helene”、“Antonius”、“Boeck”、“Maecke”、“Lempel”、“Schlich”}; int main() { int num=sizeof(vStrs)/sizeof(vStrs[0]); int len=sizeof(vStrs[0]); 字符交换[len]; char-vBuf[128]; 查*纳达; int i,j; 对于(i=0;i
和C-strcpy()处的分段故障 #包括 #包括 #包括 char*vStrs[]={“Max”、“Moritz”、“Bolte”、“Hans Huckebein”、“Helene”、“Antonius”、“Boeck”、“Maecke”、“Lempel”、“Schlich”}; int main() { int num=sizeof(vStrs)/sizeof(vStrs[0]); int len=sizeof(vStrs[0]); 字符交换[len]; char-vBuf[128]; 查*纳达; int i,j; 对于(i=0;i,c,segmentation-fault,strcpy,C,Segmentation Fault,Strcpy,和strcpy(vStrs[j],vStrs[i]),您将一个字符串文本的内容复制到另一个字符串文本中。这就像您编写了strcpy(“Max”,“Moritz”),但不能修改字符串文本(其未定义的行为) 无论如何,程序的目的是交换指向内容的指针,而不是内容本身。因此,如果按以下方式更改程序,一切都应该正常: #include <stdio.h> #include <stdlib.h> #include <string.h> char *vStrs[] = {
strcpy(vStrs[j],vStrs[i])
,您将一个字符串文本的内容复制到另一个字符串文本中。这就像您编写了strcpy(“Max”,“Moritz”)
,但不能修改字符串文本(其未定义的行为)
无论如何,程序的目的是交换指向内容的指针,而不是内容本身。因此,如果按以下方式更改程序,一切都应该正常:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
char *vStrs[] = {"Max", "Moritz", "Bolte", "Hans Huckebein", "Helene", "Antonius", "Boeck", "Maecke", "Lempel", "Schlich"};
int main()
{
int num = sizeof(vStrs) / sizeof(vStrs[0]);
int len = sizeof(vStrs[0]);
char exchnge[len];
char vBuf[128];
char *ndata;
int i, j;
for(i=0; i<num-1; i++)
{
for(j=i+1; j<num; j++)
{
if(strcmp(vStrs[j], vStrs[i]) < 0)
{
strcpy(exchnge, vStrs[j]);
strcpy(vStrs[j], vStrs[i]);
strcpy(vStrs[i], exchnge);
}
}
}
for(i=0; i<num; i++)
printf("%s\n", vStrs[i]);
return 0;
}
char*vStrs[]={“Max”、“Moritz”、“Bolte”、“Hans Huckebein”、“Helene”、“Antonius”、“Boeck”、“Maecke”、“Lempel”、“Schlich”};
int main()
{
int num=sizeof(vStrs)/sizeof(vStrs[0]);
对于(int i=0;i),因为您没有以最严格的错误检查模式运行编译器
一些人认为-Wall
意味着“所有警告”。事实并非如此。甚至连-Wall-Wextra
都没有接近“可能的最严格错误检查模式”。我将从-Wall-Wextra-pedantic-Wmissing include dirs-Wfloat equal-Wundef-Wcast align-Wwrite strings-Wlogical op-Wmissing声明-Wredundant declarations-Wshadow-Wno-system headers-Wno deprecated-Wunused变量-Wunused参数-Wunused函数-Wunused
开始,然后参考以查找您的comp是否还有更多艾勒能为你做些什么
如果您不使用GCC,请根据您选择的编译器调整最后一段。编译器是您的朋友,请给他一切可能的机会,以防止您出错
启用这些选项后,您将收到以下警告:
警告:初始化从指针目标类型[-Wdiscarded限定符]丢弃“const”限定符
因为就语言标准而言,“Max”
是char*
类型,但作为字符串文本,指向的内存是不可写的。这就是为什么
segfaults在您的计算机上。使用-Wwrite strings
,您告诉编译器改为使用字符串文本char const*
(就像使用C++时一样),这样编译器在您忽略文本的不可写性质时会生成警告
编译器警告。没有这些警告,不要离开家。您无法写入数组。字符串文字的类型为const char*您试图做什么?复制一个常量代替另一个常量?此外,此行还将导致seg错误strcpy(exchnge,vStrs[j]);最终。exchnge的长度只有3。您的许多字符串都比这长。
=sizeof(vStrs[0]);
提供指针的大小。因此缓冲区“exchnge”太小,导致崩溃。总的来说,您似乎是通过尝试和错误来编程的。这是行不通的,您必须真正了解程序中每一行的功能。@Martin Chekurov:这不是长度问题;修改字符串文字是UB,即使两个字符串的长度相同。
char *vStrs[] = {"Max", "Moritz", "Bolte", "Hans Huckebein", "Helene", "Antonius", "Boeck", "Maecke", "Lempel", "Schlich"};
int main()
{
int num = sizeof(vStrs) / sizeof(vStrs[0]);
for(int i=0; i<num-1; i++)
{
for(int j=i+1; j<num; j++)
{
if(strcmp(vStrs[j], vStrs[i]) < 0)
{
char *exchnge = vStrs[j];
vStrs[j] = vStrs[i];
vStrs[i] =exchnge;
}
}
}
for(int i=0; i<num; i++)
printf("%s\n", vStrs[i]);
return 0;
}