将字符串拆分为令牌,并将令牌拆分为两个单独的数组

时间:2018-10-19 17:14:38

标签: c++ arrays split token

我正在尝试创建一个函数readBooks,该函数打开输入文件流,读取文件和作者的列表,并用逗号隔开,文件的每一行上都有一对书和作者对(例如:Douglas Adams,The 《银河漫游指南》)。我在如何标记或分割字符串方面遇到了麻烦,以便可以使用逗号作为分隔符将作者和书名插入两个单独的数组中。任何帮助表示赞赏。

数组的大小由函数中的Capacity参数定义。数组是在调用readBooks()函数之前分配的,因此不需要动态分配它们。

这是我到目前为止的代码:

int readBooks (string filename, string titles[], string authors[], int books, int capacity){
    ifstream file;
    file.open (filename);
    if (file.fail()){
        return -1;
    }
    else{
        int i = 0;
        int j = 0;
        while (i < capacity){
            string line;
            getline (file, line);
            if (line.length() > 0){

            }
        }
    }
}

2 个答案:

答案 0 :(得分:0)

使用boost库,您可以在其中检查多个定界符,这会更简单一些。但是,您可以使用getline()搜索行尾定界符,然后使用find()查找逗号。找到逗号后,您必须确保将标题跳过,并剪掉所有空白。

让我知道这是否有意义。

#include <iostream>
#include <fstream>
#include <string>
#include "readBooks.h"

#include <algorithm>
#include <cctype>
#include <locale>

/* trim from start (in place) [Trim functions borrowed from 
 * https://stackoverflow.com/questions/216823/whats-the-best-way-to-trim-stdstring] 
 */

static inline void ltrim(std::string &s) {
    s.erase(s.begin(), std::find_if(s.begin(), s.end(), [](int ch) {
        return !std::isspace(ch);
    }));
}

// trim from end (in place)
static inline void rtrim(std::string &s) {
    s.erase(std::find_if(s.rbegin(), s.rend(), [](int ch) {
        return !std::isspace(ch);
    }).base(), s.end());
}

// trim from both ends (in place)
static inline void trim(std::string &s) {
    ltrim(s);
    rtrim(s);
}


using namespace std;

int readBooks (string filename, string titles[], string authors[], int books, int capacity){
    ifstream file;
    file.open (filename);
    if (file.fail()){
        return -1;
    }
    else{
        int i = 0;
        string line;

        while(  i < books && i < capacity && getline(file,line) ) {
            // Find the position of the comma, and grab everything before it
            string author(line.begin(), find(line.begin(), line.end(), ','));
            trim(author);
            authors[i] = author;
            // Find position of first character after the ','
            string title(find(line.begin(), line.end(), ',') + 1, line.end());
            trim(title);
            titles[i] = title;
            i++; // increment our index
        }
    }
    file.close();
    return 0;
}

这是一个名为main()的示例。

#include <iostream>
#include "readBooks.h"

int main() {

  const int capacity{1000};
  const int books{3};
  std::string authors[capacity];
  std::string titles[capacity];
  std::string filename{"booklist.txt"};

  int retval = readBooks(filename, titles, authors, books, capacity);

  return retval;
}

答案 1 :(得分:-1)

首先,如果您甚至不确定输出的大小,为什么还要使用输出数据数组(import { FormControl, FormControlLabel, FormLabel, Radio } from "@material-ui/core"; import RadioGroup from "@material-ui/core/RadioGroup/RadioGroup"; import React from "react"; import ReactDOM from "react-dom"; import Input from "@material-ui/core/Input/Input"; const MUIRadioGroup = ({ classes, isSubmitting, label, name, value, onChange, controls, InputVal, onInputChange }) => { return ( <FormControl component="fieldset"> <FormLabel component="legend">{label}</FormLabel> <RadioGroup aria-label={label} name={name} // className={classes.group} value={value} onChange={onChange} > {controls.map(({ value, disabled, label, ...rest }, i) => { return ( <FormControlLabel key={value + i} value={label ? value : InputVal} disabled={disabled || isSubmitting} control={<Radio disabled={disabled || isSubmitting} />} label={ label ? ( label ) : ( <Input id={"Ga-radio-input"} key={"Ga-radio-input"} onChange={onInputChange} name={"Ga-radio-input"} value={InputVal} /> ) } /> ); })} </RadioGroup> </FormControl> ); }; class Test extends React.Component { state = { value: undefined, // so we don't default select the radio with blank input radioInputValue: "" }; handleChange = e => { this.setState({ value: e.target.value }, () => console.log(this.state.value) ); }; handleRadioInputChange = e => { this.setState({ radioInputValue: e.target.value }, () => { console.log(this.state.radioInputValue); }); }; render() { const controls = [ { value: "1", label: "Choice 1", disabled: false }, { value: "2", label: "Choice 2", disabled: false }, { value: "", label: null, disabled: false } ]; return ( <MUIRadioGroup controls={controls} value={this.state.value} onChange={this.handleChange} isSubmitting={false} label={"Choose one:"} InputVal={this.state.radioInputValue} onInputChange={this.handleRadioInputChange} /> ); } } const rootElement = document.getElementById("root"); ReactDOM.render(<Test />, rootElement); )。 std::string[]永远是更好的解决方案。

std::vector

简而言之,它基于void readBooks(std::string const& filename, std::vector<std::string> &titles, std::vector<std::string> &authors) { std::ifstream file; // ..... // file is opened here // .... std::string temp; while (file) { if (!std::getline(file, temp, ',')) throw std::exception("File is broken?"); authors.push_back(temp); std::getline(file, temp, '\n'); titles.push_back(temp); //make sure there is no space after ',', as it'd be included in the string. //To remove such a space temp.substr(1) can be used. } } 的{​​{1}}参数。

编辑:检查是否添加了以','结尾的文件。