【问题标题】:read/write struct from text file in c++从C ++中的文本文件读/写结构
【发布时间】:2023-03-17 21:41:01
【问题描述】:

我已经被这段代码困在同一个地方一段时间了。最后决定在网上问一下。任何帮助,将不胜感激。

我已经创建了一个结构,并且可以向结构中添加数据,但仍然不确定我是否遵循了正确的方法。主要问题在于当我尝试从文本文件中读取数据时。

我似乎收到一条错误消息:

error C2678: binary '>>' : no operator found which take a left-hand 'std::ifstream' 类型的操作数(或没有可接受的转换)

结构:

struct bankDetails              //structure for bank details
{
    int acc_number;
    double acc_balance;
    double deposit_amt;
    double withdraw_amt;
    double interest_rate;
    //char acc_type;


};


struct CustDetails                     //structure for account details
{
    string cust_name;
    string cust_pass;
    bankDetails bankAccounts[99];
};

这是我为从文件中读取而编写的代码。

CustDetails loadDataFromFile ()
{
    CustDetails x;
    ifstream  dimensionsInfile; 
    dimensionsInfile.open ("storage.txt");
    for (int i=0; i < 2; i++)                                                               
    {   // write struct data from file  
        dimensionsInfile>>
        &x.bankAccounts[i].acc_balance>>
        &x.bankAccounts[i].acc_number>>
        &x.cust_nam>>
        &x.cust_pass>>
        &x.bankAccounts[i].withdraw_amt>>
        &x.bankAccounts[i].deposit_amt>>
        &x.bankAccounts[i].interest_rate>>
        cout<<"Data loaded"<<endl;
    } 
    return x;

}

写入文件的代码:

void details_save(int num,CustDetails x)
{

    string  filePath = "storage.txt";                                                                               
    ofstream  dimensionsOutfile;                                                                    

    dimensionsOutfile.open ("storage.txt");                                             
    if (!dimensionsOutfile)
        {
            cout<<"Cannot load file"<<endl;
            return ;
        }
    else
        {
            for (int i=0; i < num; i++)                                                             
                {   // write struct data from file  
                    dimensionsOutfile<<
                    &x.bankAccounts[i].acc_balance<<
                    &x.bankAccounts[i].acc_number<<
                    &x.cust_name<<
                    &x.cust_pass<<
                    &x.bankAccounts[i].withdraw_amt<<
                    &x.bankAccounts[i].deposit_amt<<
                    &x.bankAccounts[i].interest_rate<<
                    cout<<" Customer 1 stored"<<endl;
                }
            cout <<"All details have been successfully saved"<<endl;
            dimensionsOutfile.close();
        }

}

部分主要功能:

#include "stdafx.h"
#include <string>
#include <string.h>
#include <ctime>
#include <fstream>
#include <sstream>
#include <iostream>
#include <iomanip>

int main()

{
    int maxNum;
    CustDetails c;
    c = loadDataFromFile(); //loads data from the file

    {
            //This part adds and changes values
    }

    details_save(maxNum, c); //saves data back to the file
        return 0;
}

我是 C++ 的初学者,任何帮助将不胜感激。 干杯!!

【问题讨论】:

  • 您将指针保存在文件中,而不是实际数据。
  • 当前的问题是您通过指针将参数传递给各个字段。删除&amp;:输入操作员通过引用获取值。 ...而且,最重要的是:您总是需要检查 *after 读取操作是否成功(如果您只了解最后一点,您就取得了巨大的飞跃前进)。

标签: c++ visual-c++ struct iostream ifstream


【解决方案1】:

了解file formats。您可能需要指定您的(在纸上......),然后您可以使用一些 EBNF 符号来表示该规范。

您当前的代码可能误用了operator &gt;&gt;operator &lt;&lt;。你不想在文件上写指针(即使你在技术上可以),因为再次读取它们是没有意义的(因为ASLR,并且因为不能保证地址从一次运行到下一次,或者从明天你的程序的一个可执行文件会略有改进)。

您可能想做一些二进制 IO(但我不建议这样做)。然后你会使用一些像std::istream::read这样的二进制输入函数来读取记录(例如一些PODstruct)。但是你不能(有意义地)在复杂的类上做二进制 IO,比如你的 CustDetails,包含非 POD 数据,比如 std::string-s。

实际上,数据往往比软件读写数据更重要。因此,拥有一些更灵活的数据格式是有意义的(例如,您希望能够在两年内让代码的改进版本读取一些编写的数据em> 版本的代码)。

因此,通常最好使用一些文本格式(您需要对其进行定义和记录)。您可以选择一些现有的,例如JSONYAMLXMLS-expressions。您会发现许多库可以帮助您(例如,jsoncpp 用于 JSON 等...)。或者您也可以使用自己的parsing 技术。

你也可以考虑一些database,也许就像sqlite一样简单。

另请参阅serializationapplication checkpointingpersistenceportability

【讨论】:

    【解决方案2】:

    在 loadDataFromFile() 之前

    cout<<"";
    

    将“>>”替换为“;”。

    我们不能将 >> 运算符与 cout 一起使用。

    虽然有更好更简单的方法来做你正在做的事情。 fstream.h 具有直接写入和读取类或结构对象的功能。

    语法如下:

    <stream name>.read((char*)<object name>,sizeof(<struct/class name>));
    

    所以你的 loadDataFromFile 可以简化为:

    CustDetails loadDataFromFile ()
    {
    CustDetails x;
    ifstream  dimensionsInfile; 
    dimensionsInfile.open ("storage.txt");                                                              
         // write struct data from file  
         dimensionsInfile.read((char*) CustDetails, sizeof(x));   
         cout<<"Data loaded"<<endl;
         return x;
    }
    

    类似地写Write函数的定义。这将为您节省大量时间和麻烦。

    【讨论】:

      猜你喜欢
      • 2013-12-25
      • 2013-07-19
      • 1970-01-01
      • 2021-11-10
      • 2012-07-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多