2012-09-06 38 views
0

这里是我的代码:C++:为什么我得到分段错误?

#include <iostream> 
#include <stdio.h> 
#include <stdlib.h> 


using namespace std; 

struct Computer 
{ 
    char * model; 
    char * assembler; 
    int processorInt; 
}; 

int main() 
{ 
    Computer comp; 
    char* model; 
    char* assembler; 
    int processorInt; 

    cin>>model; 
    cin>>assembler; 
    cin>>processor int; 

    comp.model = model; 
    comp.assembler = assembler; 
    comp.processorInt = processorInt; 

    return 0; 
} 

//如果我这样做,它的工作原理,但如果我用另一种方式做,这让段错误

#include <iostream> 
#include <stdio.h> 
#include <stdlib.h> 


using namespace std; 

struct Computer 
{ 
    char * model; 
    char * assembler; 
    int processorInt; 
}; 

void setValues() 
{ 
    Computer comp; 
    char* model; 
    char* assembler; 
    int processorInt; 

    cin>>model; 
    cin>>assembler; 
    cin>>processor int; 

    comp.model = model; 
    comp.assembler = assembler; 
    comp.processorInt = processorInt; 
} 

int main() 
{ 
    setValues(); 

    return 0; 
} 

那么是什么原因呢?

我的目标是创建结构,其中我可以节省约每一个“电脑”的一些信息,然后做一个可能性编辑任何结构,然后通过procesorInt整个数组排序的数组。但我甚至无法创建一个正常的可编辑结构。

+5

你输入一个未分配,未初始化的指针。你需要使它指向一些预先分配的内存,为它分配内存(涉及第一部分),或者最重要的是使用'std :: string'。 – chris

+1

什么是'cin >>处理器int;'? –

+6

第一个工作,因为你不走运。第二个不行,因为你很幸运。 –

回答

2

这两个版本都不能正常工作,您正尝试将数据读入未初始化的指针。只要声明例如char* model;给你一个未初始化的指针:它可以指向内存中的任何点。当您尝试使用cin >>在该位置存储字符串时,您将写入不属于您的内存。这可能会出现段错误,或者它可能看起来有效。

刚刚宣布char*不给你的字符串空间:如果您使用的是标准的C字符串,那么你就需要给他们一些数据:使一个固定大小的你char指针数组,或者使用malloc来分配一个字符串缓冲区:

char model[MAX_STRING_LENGTH]; 

或者使用malloc,但要注意,你需要free此内存后:

char *model = malloc(MAX_STRING_LENGTH); 

现在,如果你要使用标准的C字符串和cin在一起,你根本不应该使用>>:没有办法限制输入大小。请使用cin.getlineMAX_STRING_LENGTH作为限制(有关详细信息,请参阅文档中的示例)。

但绝对宁愿使用std::string来代替:如果你这样做,那么你就不需要为自己提供空间来处理字符串,而且你的代码根本不需要改变很多。

+0

感谢您解释,在c#后这个主题对我来说很奇怪 –

+0

您无法从输入安全地读取到固定大小的缓冲区;没有办法来防止超限。 'std :: string'是这里唯一明智的选择。 –

+0

@MikeSeymour非常感谢Mike,这非常重要,我已经多加了一点。 – pb2q

5

您正在阅读到不随地指着char指针。没有空间来存储读取的字符。

容易得多是使用std::string,beause将automayically调整自身,以稳住老从输入的字符。

Computer comp; 
std::string model; 
std::string assembler; 
int processorInt; 

cin>>model; 
cin>>assembler; 
cin>>processorInt; 
+0

非常感谢,但练习的一部分是使用类C字符串 –

+0

@RomaBugaian,然后我更喜欢'std :: unique_ptr '。这样你就可以减少一个担心的问题。但是,根据C字符串是定义为字符数组还是必须自己管理的指针,您可能必须选择比智能指针更差的选项。 – chris

+0

@RomaBugaian:那么我希望这个练习的重点是教你缓冲区溢出的危险和消毒输入的重要性。您无法安全地将C风格的字符串与C++风格的格式化输入结合使用。 –

相关问题