如何使用 istream_iterators 拆分等式?

how to use istream_iterators to split an equation?

我试图将像 ( 1 + 2 ) 这样的字符串拆分成一个向量,当使用 istream_iterators<string> 时它不会拆分括号所以我得到像

这样的向量输出

(1 , + , 2) 当我想要 ( , 1, + , 2 ,)

是否可以使用 istream_iterators 来实现这一点?

string eq = "(1 + 2)";

istringstream ss(eq);
istream_iterator<string> begin(ss);
istream_iterator<string> end;
vector<string> vec(begin, end);

我认为您无法使用 istream_iterator 来完成。相反,只需手动完成:

vector<string> vec;
vec.reserve(eq.size() / 4); // rough guess
bool in_number = false;
for (char ch : eq) {
    if (isspace(ch)) {
        in_number = false;
    } else if (isdigit(ch)) {
        if (in_number) {
            vec.back().push_back(ch);
        } else {
            vec.emplace_back(1, ch);
            in_number = true;
        }
    } else {
        vec.emplace_back(1, ch);
        in_number = false;
    }
}

您可以通过创建自定义类型 Token 并将其与 istream_iterator。额外功能:此代码将解析多个数字、多个运算符和嵌套表达式。所以享受吧。 :)

#include <iterator>
#include <string>
#include <sstream>
#include <vector>
#include <iostream>
#include <cctype>

using namespace std;

class Token {
private:
  string val;
public:
  Token() : val("") {}
  Token(string& v) : val(v) {}
  friend istream& operator>>(istream &in, Token& tok);
  friend ostream& operator<<(ostream &out, Token& tok);
};

istream& operator>>(istream &in, Token& tok) {
  char c;
  string v;
  if (in >> c) {
    if (isdigit(c)) {
      v.push_back(c);
      while (in >> c && isdigit(c)) {
    v.push_back(c);
      }
      in.putback(c);
    } else if (c == ' ') {
      while (in >> c && c == ' ') ;
      in.putback(c);
    } else {
      v.push_back(c);
    }
  }
  tok = v;
  return in;
}

ostream& operator<<(ostream &out, Token& tok) {
  out << tok.val;
  return out;
}

int main() {
  string eq = "(1 + 2)";
  //eq = "(100 + 200)"; // multiple digits
  //eq = "(100 + 200 * 300)"; // extra operator
  //eq = "(100 + (200 * 300))"; // nested parens

  istringstream ss(eq);
  istream_iterator<Token> begin(ss);
  istream_iterator<Token> end;
  vector<Token> vec(begin, end);
  for (auto& x : vec) {
    cout << "[" <<  x << "] ";
  }
  cout << endl;
}