c++ 可以智能判断csv域包裹符 源码
时间: 2023-11-29 09:05:11 浏览: 29
以下是一个例子,展示了如何使用状态机来智能判断CSV域包裹符的C++代码:
```c++
#include <iostream>
#include <fstream>
#include <string>
#include <vector>
using namespace std;
enum CSVState {
UnquotedField,
QuotedField,
QuotedQuote
};
vector<string> readCSVRow(const string& row) {
CSVState state = UnquotedField;
vector<string> fields {""};
size_t i = 0; // index of the current field
for (char c : row) {
switch (state) {
case UnquotedField:
switch (c) {
case ',': // end of field
fields.push_back("");
i++;
break;
case '"': state = QuotedField;
break;
default: // other character
fields[i].push_back(c);
break;
}
break;
case QuotedField:
switch (c) {
case '"': state = QuotedQuote;
break;
default: // other character
fields[i].push_back(c);
break;
}
break;
case QuotedQuote:
switch (c) {
case ',': // , after closing quote
fields.push_back("");
i++;
state = UnquotedField;
break;
case '"': // "" -> "
fields[i].push_back('"');
state = QuotedField;
break;
default: // end of quote
state = UnquotedField;
break;
}
break;
}
}
return fields;
}
vector<vector<string>> readCSV(const string& filename) {
vector<vector<string>> rows;
ifstream file(filename);
string row;
while (getline(file, row)) {
rows.push_back(readCSVRow(row));
}
return rows;
}
int main() {
auto rows = readCSV("example.csv");
for (const auto& row : rows) {
for (const auto& field : row) {
cout << field << " ";
}
cout << endl;
}
return 0;
}
```
以上代码会将CSV文件中的每一行解析为一个字符串向量,并且自动识别出域包裹符。如果当前字段需要被包裹,则将状态机的状态切换到`QuotedField`,直到遇到另一个域包裹符或行尾。如果当前状态为`QuotedField`,则会将所有字符都作为字段的一部分,直到遇到另一个域包裹符。如果当前状态为`QuotedQuote`,则表示遇到了两个连续的域包裹符,因此会将其视为一个包裹符。