C++ 尝试写入二进制文件,获取文本文件

C++ 尝试写入二进制文件,获取文本文件,c++,binaryfiles,C++,Binaryfiles,试图通过将游戏角色写入二进制文件来保存我的游戏。不幸的是,我的二进制文件正在写入该文件,就好像它是一个文本文件一样 如果我只是实例化一个字符串并调用该字符串的save函数,它将完美地写入二进制文件。但是,如果我从CharacterSave函数调用相同的函数,它只是将文件显示为文本文件,而不是二进制文件 调用层次结构会发生变化 Character.Save()调用字符串Save,该字符串将写入二进制文件 Character.Save()调用palk(即coinpalk)Save,它将写入二进制文件

试图通过将游戏角色写入二进制文件来保存我的游戏。不幸的是,我的二进制文件正在写入该文件,就好像它是一个文本文件一样

如果我只是实例化一个字符串并调用该字符串的save函数,它将完美地写入二进制文件。但是,如果我从CharacterSave函数调用相同的函数,它只是将文件显示为文本文件,而不是二进制文件

调用层次结构会发生变化

  • Character.Save()调用字符串Save,该字符串将写入二进制文件

  • Character.Save()调用palk(即coinpalk)Save,它将写入二进制文件

  • Character.Save()调用钱包(即背包)Save,它调用动态数组Save,它将元素数写入二进制文件,并调用potion Save方法,它调用字符串Save方法

  • 编辑:解决了问题。我不知道怎么做,但只是制作另一个.dat文件就解决了这个问题。

    调用保存函数

    //Create instance of binary file object
    std::ofstream file("game.dat", std::ios::out | std::ios::binary);
    
    //Check if file is open
    if(file.is_open())
    {
        //Save character
        myFavoriteCharacter.Save(file);
    
        //Close the file
        file.close();
    }
    else
        std::cout << "\nFile did not open! " << std::endl;
    
    void Character::Save(std::ofstream & file)
    {
        mName.Save(file);
        mPouch.Save(file);
        mPurse.Save(file);
    }
    
    void String::Save(std::ofstream & file)
    {
        int tempLength = 0;
        tempLength = this->getLength();
    
        //Write the length of the string
        file.write(reinterpret_cast<char *>(&tempLength), sizeof(int));
    
        //Write the string
        file.write(reinterpret_cast<char *>(this->mStr), tempLength + 1);
    }
    
    void CoinPouch::Save(std::ofstream & file)
    {
        file.write(reinterpret_cast<char *>(&mPlatinum), sizeof(int));
        file.write(reinterpret_cast<char *>(&mGold), sizeof(int));
        file.write(reinterpret_cast<char *>(&mSilver), sizeof(int));
        file.write(reinterpret_cast<char *>(&mCopper), sizeof(int));
    }
    
    void DynamicArray::Save(std::ofstream & file)
    {
        //Write the number of elements
        file.write(reinterpret_cast <char *>(&mElements), sizeof(int));
    
        //Save each element
        for(int i = 0; i < mElements; i++)
            mArray[i].Save(file);
    }
    
    void Potion::Save(std::ofstream & file)
    {
        mName.Save(file);
        mDescription.Save(file);
        mPotency.Save(file);
        mCost.Save(file);
    }
    
    字符串保存功能

    //Create instance of binary file object
    std::ofstream file("game.dat", std::ios::out | std::ios::binary);
    
    //Check if file is open
    if(file.is_open())
    {
        //Save character
        myFavoriteCharacter.Save(file);
    
        //Close the file
        file.close();
    }
    else
        std::cout << "\nFile did not open! " << std::endl;
    
    void Character::Save(std::ofstream & file)
    {
        mName.Save(file);
        mPouch.Save(file);
        mPurse.Save(file);
    }
    
    void String::Save(std::ofstream & file)
    {
        int tempLength = 0;
        tempLength = this->getLength();
    
        //Write the length of the string
        file.write(reinterpret_cast<char *>(&tempLength), sizeof(int));
    
        //Write the string
        file.write(reinterpret_cast<char *>(this->mStr), tempLength + 1);
    }
    
    void CoinPouch::Save(std::ofstream & file)
    {
        file.write(reinterpret_cast<char *>(&mPlatinum), sizeof(int));
        file.write(reinterpret_cast<char *>(&mGold), sizeof(int));
        file.write(reinterpret_cast<char *>(&mSilver), sizeof(int));
        file.write(reinterpret_cast<char *>(&mCopper), sizeof(int));
    }
    
    void DynamicArray::Save(std::ofstream & file)
    {
        //Write the number of elements
        file.write(reinterpret_cast <char *>(&mElements), sizeof(int));
    
        //Save each element
        for(int i = 0; i < mElements; i++)
            mArray[i].Save(file);
    }
    
    void Potion::Save(std::ofstream & file)
    {
        mName.Save(file);
        mDescription.Save(file);
        mPotency.Save(file);
        mCost.Save(file);
    }
    

    强制VisualStudio2012打开一个名为“game2.dat”的新文件,它成功了。现在我的二进制文件有一个十六进制转储,而不是它给我的普通文本文件。我真的不明白为什么会这样,但确实如此


    感谢那些阅读/回复的人。

    迫使VisualStudio2012打开了一个名为“game2.dat”的新文件,它成功了。现在我的二进制文件有一个十六进制转储,而不是它给我的普通文本文件。我真的不明白为什么会这样,但确实如此


    感谢那些阅读/回复的人。

    您主要是在保存字符数据。字符数据在文本或二进制中看起来相同。那么,您看到了什么确保这个文件是文本而不是二进制文件?我不认为你的代码中有任何错误(但当然有一大堆东西丢失了,可能是错误的、不一致的或其他的)。但是,我很好奇,您如何确定该文件“不是二进制文件”。所有文件都是二进制文件,文本文件恰好只有可打印的“char”值和一小部分控制字符(换行符、制表符和其他一些字符)。如果你将代码的输出作为文件打印到屏幕上,我希望看到的主要是文本字符串,因为这似乎是你正在保存的…@Mats-peterson——我不知道如何保存,但我将“game.dat”改为“game2.dat”(即强制它打开一个新文件),结果成功了。我的代码现在以二进制格式保存,而不是ASCII(即文本)格式。可能是Visual Studio的问题?@john当您编写二进制文件时,Visual Studio会创建文件的十六进制转储。您可以看到第一列的十六进制地址行。第二列代码的实际字节数。然后是第三列的实际文本。以上只是打印文本。在写入文件之前,可能需要“std::ios::trunc”来截断(使大小为零)文件?您主要是保存字符数据。字符数据在文本或二进制中看起来相同。那么,您看到了什么确保这个文件是文本而不是二进制文件?我不认为你的代码中有任何错误(但当然有一大堆东西丢失了,可能是错误的、不一致的或其他的)。但是,我很好奇,您如何确定该文件“不是二进制文件”。所有文件都是二进制文件,文本文件恰好只有可打印的“char”值和一小部分控制字符(换行符、制表符和其他一些字符)。如果你将代码的输出作为文件打印到屏幕上,我希望看到的主要是文本字符串,因为这似乎是你正在保存的…@Mats-peterson——我不知道如何保存,但我将“game.dat”改为“game2.dat”(即强制它打开一个新文件),结果成功了。我的代码现在以二进制格式保存,而不是ASCII(即文本)格式。可能是Visual Studio的问题?@john当您编写二进制文件时,Visual Studio会创建文件的十六进制转储。您可以看到第一列的十六进制地址行。第二列代码的实际字节数。然后是第三列的实际文本。以上只是打印文本。在写入文件之前,可能需要“std::ios::trunc”来截断(使大小为零)文件?文件名显然不会改变它是作为二进制文件还是文本文件写入的。如果我强制编译器将其二进制输出生成一个名为“foo.txt”的文件,它仍然是二进制的。您的代码中有错误,我认为是您没有打开新文件。@MatsPeterson为什么我需要新文件?ofstream不会覆盖旧文件中的所有内容吗?不,你是对的,它会根据你已经给出的参数创建一个新文件。因此,上面关于MS猜测文件内容的解释可能是正确的,可能只是您保存了一些稍微不同的数据,这些数据触发了“visual studio打开文件的方式”的差异。文件名显然不会改变它是作为二进制文件还是文本文件写入的。如果我强制编译器将其二进制输出生成一个名为“foo.txt”的文件,它仍然是二进制的。您的代码中有错误,我认为是您没有打开新文件。@MatsPeterson为什么我需要新文件?ofstream不会覆盖旧文件中的所有内容吗?不,你是对的,它会根据你已经给出的参数创建一个新文件。因此,上面关于MS猜测文件内容的解释可能是正确的,可能只是因为您保存了一些稍微不同的数据,从而触发了“VisualStudio如何打开文件”的差异。