c++ 尝试从指定行(给定字符串输入)到另一个指定行(用于预期输出)获取信息

kokeuurv  于 2022-11-27  发布在  其他
关注(0)|答案(1)|浏览(135)

我目前正在尝试构建一个函数,它接受用户的输入,在一个字符串(从一个文本文件)中搜索该输入,然后从该行读取该字符串到预期的“结束”行。

#include <iostream>
#include <fstream>

using namespace std;

int main() {
    string dataFile, dataSFile, accNum, Name, Number, SS, Address, Bal, endV;
    dataFile = "accounts.txt";
    ifstream fin1(dataFile);
    if(!fin1.is_open()){
        cout << "\033[91mError Gathering Account Information.\nPlease contact your IT Administrator.\n \n";
        return 0;
    }
    getline(fin1, dataSFile, '\0');
    ofstream fout1(dataFile, std::ios_base::app);
    cout << "Please enter the acc #" << endl;
    getline(cin, accNum);
    if(dataSFile.find(accNum) != std::string::npos){
    fin1 >> Name >> "\0" >> Number >> "\0" >> SS >> "\0" >> Address >> "\0" >> Bal >> "\0" >> endV;
    cout << "[" << accNum << "]" << endl;
    cout << Name << endl;
    cout << Number << endl;
    cout << SS << endl;
    cout << Address << endl;
    cout << Bal << end;
    }
    return 0;
}

在“accounts. TXT”中,存在以下项目。

[10111]
Gerald Gray
800-111-1111
222-22-2222
19 Driveway Dr, Grayville, CT 00000
$0
[end]

[10222]
James Murray
800-222-2222
333-33-3333
20 Driveway Dr, Grayville, CT 00001
$500
[end]

我想使用file.find() != std::string:npos在文本中查找字符串,确定位置,然后选择下面的行,直到它到达[end]

示例:

请输入帐号10111
[10111]杰拉尔德·格雷800-111-1111 222-22-2222康涅狄格州格雷维尔19车道博士00000 0
end of output
任何和所有的帮助都是感激不尽的!谢谢!
我只尝试过使用getline和fin,因为我没有其他方法来这样做。

t5fffqht

t5fffqht1#

使用输入字符串流而不是文件流的可能解决方案:

  • 有一个account结构体和一个accounts无序Map。

可以打印帐户对象(例如,使用std::cout << account)。

  • 主代码只调用parse,传递一个输入流,并接收一个accountsMap。
  • parse函数不断从输入流中阅读行。

只要找到与帐号匹配的行,它就会尝试从下一行读取帐户字段的其余部分。
如果它无法执行此操作(因为没有要读取的行,或者因为读取的某些行与预期模式不匹配),它将继续循环或退出循环。
否则,它会将新帐户添加到Map中。

  • 帐户ID和余额使用正则表达式进行匹配。

Demo(https://godbolt.org/z/x6GrfocWc)

#include <fmt/ostream.h>
#include <iostream>  // cout
#include <regex>
#include <sstream>  // istringstream
#include <unordered_map>

struct account {
    int id;
    std::string name;
    std::string phone_no;
    std::string ss;
    std::string address;
    int balance;

    friend std::ostream& operator<<(std::ostream& os, const account& a) {
        fmt::print(os,
            "id: {}, name: '{}', phone_no: '{}', ss: '{}', address: '{}', balance: {}",
            a.id, a.name, a.phone_no, a.ss, a.address, a.balance);
        return os;
    }
};

using accounts = std::unordered_map<int, account>;

accounts parse(std::istringstream& iss) {
    accounts ret{};
    for (std::string id_line{}; std::getline(iss, id_line);) {
        account acc{};
        std::regex id_pattern{"\\[([[:digit:]]+)\\]"};
        std::regex balance_pattern{"\\$([[:digit:]]+)"};
        std::string end_pattern{"[end]"};
        std::smatch id_matches{};
        std::smatch balance_matches{};
        std::string balance_line{};
        std::string end_line{};

        if (std::regex_match(id_line, id_matches, id_pattern) and
            std::getline(iss, acc.name) and
            std::getline(iss, acc.phone_no) and
            std::getline(iss, acc.ss) and
            std::getline(iss, acc.address) and
            std::getline(iss, balance_line) and
            std::regex_match(balance_line, balance_matches, balance_pattern) and
            std::getline(iss, end_line) and
            end_line == end_pattern) {

            acc.id = std::stoi(id_matches[1]);
            acc.balance = std::stoi(balance_matches[1]);
            ret.insert({acc.id, acc});
        }
    }
    return ret;
}

int main() {
    std::istringstream iss{
        "[10111]\n"
        "Gerald Gray\n"
        "800-111-1111\n"
        "222-22-2222\n"
        "19 Driveway Dr, Grayville, CT 00000\n"
        "$0\n"
        "[end]\n"
        "\n"
        "[10222]\n"
        "James Murray\n"
        "800-222-2222\n"
        "333-33-3333\n"
        "20 Driveway Dr, Grayville, CT 00001\n"
        "$500\n"
        "[end]\n"
    };
    auto accs{parse(iss)};
    for (const auto& [key, value] : accs) {
        std::cout << value << "\n";
    }
}

// Outputs:
//
//   id: 10222, name: 'James Murray', phone_no: '800-222-2222', ss: '333-33-3333', address: '20 Driveway Dr, Grayville, CT 00001', balance: 500
//   id: 10111, name: 'Gerald Gray', phone_no: '800-111-1111', ss: '222-22-2222', address: '19 Driveway Dr, Grayville, CT 00000', balance: 0

相关问题