2014-10-20 125 views
5

使用:MSVS2012C++:访问冲突写入位置

代码

elemalg.h

#include <vector> 
#include <string> 
#include <fstream> 

class ElemAlg 
{ 
private: 
std::string difficultlyLevel, question, answerToRead; 
std::vector<std::string> questions, answers; 

std::vector<std::string> GetQuiz(int); 
}; 

elemalg.cpp

#include "elemalg.h" 

std::vector<std::string> ElemAlg::GetQuiz(int difficulty) 
{ 
if (difficulty == 1) { difficultyLevel = "algE"; } 
if (difficulty == 2) { difficultyLevel = "algM"; } 
if (difficulty == 3) { difficultyLevel = "algH"; } 
if (difficulty == 4) { difficultyLevel = "algVH"; } 

std::ifstream fin(difficultyLevel + ".txt"); 
while (std::getline(fin, question)) { questions.push_back(question); } 
fin.close(); 

std::ifstream fin2(difficultyLevel + "Answers.txt"); 
while (std::getline(fin2, answerToRead)) { answers.push_back(answerToRead); } 
fin2.close(); 

return questions; 
} 

MathTutor.cpp

#includes etc 
ElemAlg *ea; 
ea->GetQuiz(1); 

GetQuiz绝对传递整数1和4之间,之前被调用的方法

difficultyLevel是在头文件中定义的字符串这是验证。

编译器一旦遇到第一个if函数就会抛出未处理的异常和访问冲突写入位置。

如果我删除if函数并将difficultyLevel定义为algE只是为了测试相同的问题。

如果我删除difficultyLevel完全公正公开的文件作为"algE.txt""algEAnswers"然后我得到了同样的问题,但在不同的存储位置,一旦代码打while循环。

+0

什么是'difficultyLevel'到底是什么? – 2014-10-20 14:48:39

+0

该参数应该在函数内用assert而不是outside来验证。如果问题是一个全局变量,我不知道你为什么试图返回它。 – 2014-10-20 14:49:31

+0

[MCVE](http://stackoverflow.com/help/mcve)或者它没有发生。 – Angew 2014-10-20 14:49:33

回答

13

你的问题是在这里:

ElemAlg *ea; 
ea->GetQuiz(1); 

你不是创造ElemAlg一个实例,所以你调用一个未初始化的指针的成员函数。

由于您调用的成员函数不是虚拟的,因此编译器不需要执行任何运行时查找,这就是为什么调用要去GetQuiz。但是,this指针将是垃圾(因为ea未初始化),所以当您访问成员变量(例如difficultyLevel)时,您将有未定义的行为。在你的情况下,未定义的行为导致访问冲突。

要么初始化ea

ElemAlg *ea=new ElemAlg; 
ea->GetQuiz(1) 

,或者,如果你不需要它分配在堆上只是做:

ElemAlg ea; 
ea.GetQuiz(1) 
+1

非常感谢你...我的程序是不同的,但它帮助我解决了我的问题... 我只是用新的关键字 更改内存分配语句在语句中获得相同的错误:'MyQueue * newnode =(MyQueue *) malloc(sizeof(MyQueue));' \t \t 将上面的语句更改为:'MyQueue * newnode = new MyQueue;'' – 2016-06-29 12:12:52