【问题标题】:Program works fine in VS 2008, throws exception in VS 2010 at the very end of program程序在 VS 2008 中运行良好,在程序结束时在 VS 2010 中抛出异常
【发布时间】:2014-10-22 22:12:33
【问题描述】:

我正在使用二进制/直接访问写入文件。在 2008 年的工作就像一个魅力,但在 2010 年的第 128 行运行时创建了一个异常:Unhandled exception at 0x535dad54 (msvcp100d.dll) in HovedProsjekt.exe: 0xC0000005: Access violation writing location 0xfeeefeee.

单击错误会将我带到 xutility,其中第 201 行:_Pnext != 0; *_Pnext = (_Pnext)->_Mynextiter) 将被执行。我查看了微软的“重大更改”页面,但没有运气。我正在以明文形式复制/粘贴整个代码,因此没有过时的库。我已经尝试了启用和禁用 _HAS_ITERATOR_DEBUGGING 和 _SECURE_SCL 的所有组合。我根据其他用户的建议更改了我的问题,以精简我的代码。

//Miniprosjekt.cpp

#include <iostream>
#include <fstream>
#include <string>
using namespace std;
bool sjekkForOverskriving(void);
void LagFil(void);
void LeggTil();
void skrivUtFeil();

class Feil{
    friend ostream& operator<<(ostream&, Feil);
    friend istream& operator>>(istream&, Feil&);
protected:
    int ID;
    int prioritet;
    string dato;
    char beskrivelse[300];
    char skrevetAv[30];
public:
    Feil();
    Feil(int, int, string, string, string);
};

Feil::Feil(){ //Default constructor
    ID = 0;
    prioritet = 1;
    dato = "01.01.1900";
    beskrivelse[0] = ' ';
    skrevetAv[0] = ' ';
}

Feil::Feil(int id, int pri, string d, string beskr, string navn){ //Constructor
    ID = id;
    prioritet = pri;
    dato = d;
    strcpy(beskrivelse, beskr.c_str());
    strcpy(skrevetAv, navn.c_str());
}


ostream& operator<<(ostream& out, Feil enfeil) //Overloader << operator, allowing for: cout << Feil afeil
{
    out << "Id nr: " << enfeil.ID << "\nSkrevet av: " << enfeil.skrevetAv  << "\nDato: " <<
        enfeil.dato << "\nPrioritet: ";
    if(enfeil.prioritet == 1)out << "Lav";
    else if(enfeil.prioritet == 2)out << "Middels";
    else out << "Høy";
    out << "\nBeskrivelse:\n" << enfeil.beskrivelse << endl;
    return out;
}

istream& operator>>(istream& in, Feil& enfeil) //Overloader >> operator: allowing for cin >> Feil afeil
{
    in >> enfeil.ID >> enfeil.dato >> enfeil.beskrivelse >> enfeil.skrevetAv;
    return in;
}

int main(void){

    LagFil();
    LeggTil();
    skrivUtFeil();

    return 0;
}



void LagFil(void){ //Creates a file with 500 empty "feil" objects
    const int MAXFEIL = 500;
    Feil enfeil;
    ofstream utFil;
    utFil.open("FeilTeller.dat");
    utFil << 0;
    utFil.close();
    utFil.open("Feilmeldinger.dat", ios::out | ios::binary);
    for(int a = 0; a <= MAXFEIL; a++){ //Fills the file with empty "Feil" objects
        utFil.write(reinterpret_cast <const char*>(&enfeil), sizeof(enfeil));
    }
    utFil.close();
}

void LeggTil(){
    int ID;
    ifstream innFil;
    innFil.open("FeilTeller.dat");
    innFil >> ID;
    innFil.close();
    fstream fil;
    fil.open("FeilTeller.dat");
    ID++; //Opens feilteller.dat, reads how many objects have already been created. Adds one to that to append.
    fil << ID;
    fil.close();
    int pri = 1;
    string beskrivelse = "test";
    string dato = "test2";
    string skrevetAv = "test3";
    Feil enfeil(ID, pri, dato, beskrivelse, skrevetAv);
    fil.open("Feilmeldinger.dat", ios::out | ios::in | ios::binary);
    fil.seekp((ID - 1) * sizeof(enfeil));
    fil.write(reinterpret_cast <const char*>(&enfeil),
            sizeof(Feil));
    fil.close();
}

void skrivUtFeil(){
    int idnr = 1;
    //for(int i = 0; i < 2; i++){
    Feil enfeil;
    int antallFeil;
    ifstream innFil;
    innFil.open("FeilTeller.dat");
    innFil >> antallFeil;
    innFil.close();
    innFil.open("Feilmeldinger.dat", ios::in | ios::binary);
    innFil.read(reinterpret_cast <char*>(&enfeil),
            sizeof(Feil));
    innFil.clear();
    //Prints out Feil with ID "idnr"
    innFil.seekg((idnr - 1) * sizeof(enfeil));
    innFil.read(reinterpret_cast <char*>(&enfeil),
            sizeof(Feil));
    cout << enfeil << endl;
    cout << "Totalt antall feil: " << antallFeil << endl;
    system("pause");
    innFil.close();
    //}
} //Exception on this line

【问题讨论】:

  • 只要谷歌“0xfeeefeee”,它就是一个神奇的数字。
  • 真的是minimal的例子吗?

标签: c++ visual-studio-2010 visual-studio-2008 incompatibility


【解决方案1】:

你的类Feil 包含string dato,所以它是not trivially copyable。因此,将其作为原始二进制数据写入和读取是非法的。

如果你这样做会发生什么? std::string 包含一个指向字符数组的指针,所以你写它的值,而不是内容。当你读取它时,你将相同的值读入指针,但它指向的是垃圾。

【讨论】:

    猜你喜欢
    • 2012-11-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-03-02
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多