尝试读取对象矢量时程序崩溃

时间:2013-08-29 15:49:05

标签: c++ stl stdvector

我有以下具有vector of objects的类。当我使用类对象读取vector的值时,程序崩溃。我甚至试图放入try block,但是控件不会进入catch block

这本书类:

class Book
{
    public:
        char isbn[11];
        char name[50];
        char author_name[50];
        char pub_name[50];
        char edition[10];
        float cost;
        char dept[10];
        int  count;
        char id[8];

};

这是Library类,其中包含vector of class Book

class Library
{
    public:
        char l_name[50];
        char admin_name[50];
        int phone_no;
        char location[50];
        vector<Book> v;
};

这是主要功能

int main()
{

    Library lib; //LIBRARY OBJECT
    Book b; //BOOK OBJECT

        fstream fp("library1.bin",ios::in | ios::binary); //OPEN FILE IN READ MODE
        if(!fp) cout<<"reading failed...";
        try
        {

        fp.read(reinterpret_cast<char *>(&lib),sizeof(lib)); //READ LIBRARY DETAILS
        if(fp.bad() == true) cout<<"Read failure..."<<endl;
        fp.close();

        cout<<"Enter ISBN number:"; cin>>b.isbn; //READ ISDN NUMBER FROM USER



            for(int i=0;i<lib.v.size();i++) //CHECK WHETHER BOOK ALREADY EXISTS
            {
                Book b1 = lib.v[i];
                if(strcmp(b1.isbn,b.isbn) == 0)
                {
                    lib.v[i].count++;
                }
            }
      } 
      catch(exception& e) //CATCH ANY EXCEPTIONS
      {
        cout<<"Error:"<<e.what()<<endl;
      }
      catch(...) //CATCH ANY UNCAUGHT EXCEPTIONS
      {
        cout<<"Unknown error occured:";
      }
}

当我试图检查ISDN号码时程序崩溃。

3 个答案:

答案 0 :(得分:2)

包含vector的基础数据的内存未存储在vector类本身中,只有指向它的指针存储在那里。

因此,当您执行fstream::read时,您正在使用指向内存中某个随机位置的指针(vector数据在您编写时所在的位置初始化此vector,可能无法访问或数据早已消失,除非您在程序的当前运行期间编写并且vector仍在范围内),因此任何访问数据的尝试都将导致未定义的行为。

我建议您不要尝试使用fstream::read直接恢复您的课程,因为要让它工作可能有点困难(更不用说随之而来的众多可能的问题),而是写作/逐个读取文件中的成员。

答案 1 :(得分:1)

您的示例中可能存在一些丢失的代码,但我怀疑问题是您在向量上使用[]而未使用大小构造函数resizepush_back来实际增加矢量的大小。

答案 2 :(得分:0)

您不能使用istream::read来读取矢量,您必须使用循环并单独读取每个矢量项。

出于同样的原因,您不应该使用ostream::write来编写矢量。虽然它可以在不崩溃的情况下工作,但它不会写任何对文件有用的东西。您应该再次使用循环来单独写入向量中的每个项目。首先编写矢量的大小可能也是有帮助的,所以当你读回它时你知道矢量中有多少项。

换句话说,C ++中的二进制I / O并不像你想象的那么简单。你还有一些工作要做。