我有一个格式为文本的文件:
a 1 b 6 e 4 h 2
r 5 q 1 a 2 e 2 b 3
高达 300k 行。每个字符都跟随它的值。我想逐行读取此文件,并在同一行中每 2 个字符之间进行配对。第一行的结果:
(a,b)
(a,e)
(a,h)
(b,e)
(b,h)
(e,h)
我也计算每对的频率。代码:
using namespace std;
std::map<std::pair< char, int>, int> CharP;
struct Mydata
{
char myString;
float value;
friend std::istream &operator>>(std::istream &is, Mydata &d) {
{
string line;
std::getline(is,line);
return is >> d.myString>> d.value;
}
};
int main()
{
std::ifstream in("Data.txt");
std::vector<Mydata> data{ std::istream_iterator<Mydata>(in), std::istream_iterator<Mydata>() };
for (std::vector<Mydata> ::iterator current = data.begin(); current != data.end(); ++current)
{
char a = current->myString;
for (std::vector<Mydata> ::iterator current2 = ++current; current2 != data.end(); ++current2)
{
char b = current2->myString;
auto itt = CharP.find(std::make_pair(b, a));
++CharP[(itt != CharP.end()) ? std::make_pair(b, a) : std::make_pair(a, b)];
}
--current;
}
cout << " \nPress any key to continue\n";
system("PAUSE");
return 0;
}
我遇到了这个错误: 二进制“>>”:未找到采用“Mydata”类型的右手操作数的运算符(或没有可接受的转换)。
我还有一个问题,因为我有大文件,我想知道是否有其他方法比附加代码更快。
最佳答案
在没有查看其余代码的情况下,我想我可以肯定地说这就是问题所在:
friend std::istream& getline(std::istream &is, Mydata &d)
您是否打算在此声明中重载提取器?如果是这样,您应该知道提取器是一个运算符,即operator>>()
。将 getline
替换为 >>>
:
friend std::istream& operator>>(std::istream &is, Mydata &d);
此外,以下内容非常不可读:
++CharP[(itt != CharP.end()) ? std::make_pair(b, a) : std::make_pair(a, b)];
将其替换为:
if (itt != CharP.end()) { auto p = std::make_pair(b, a); ++CharP[p]; } else { auto p = std::make_pair(a, b); ++CharP[p]; }
关于C++使用getline从文本文件数据类型作为结构读取,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21667873/