#include <iostream>
#include<vector>
#include<sstream>
using namespace std;

int main() {
    //可以考虑使用map容器,将文件名和行号作为key值,报错次数作为value值,每处理一个报错信息时判断map是否有相同key,有则value+1,没有则插入新值。最后需要输出最新的八条记录,因此我们最好在key中增加一个值用来代表插入时的序号,最后按照序号来输出最新的记录。但是这样会涉及到更复杂的字符串处理与大小比较。我们可以在value中加一个int存储插入时的序号,最后遍历容器map只输出其中序号最大的八条记录;
    //也可以考虑使用vector容器来存储,每一个元素包括了文件名和行数和报错次数,由于我们每处理一个报错信息就插入容器,因此每个元素的下标就代表插入的顺序,最后我们输出末尾的八条记录即可。如果有相同的报错信息(文件名和行号相同),只需要将报错次数加一即可。
        //报错信息类
    class err
    {
    public:
        string m_name;//文件名
        string m_line;//错误行号
        int m_count;//报错次数
    };

    vector<err> e_vec;//存放所有的错误信息
    string error;//每次处理一行
    while (getline(cin, error))
    {
        stringstream ss(error);
        string tmp;
        while (getline(ss, tmp, '\\'));//读取到最后一段,包含文件名和次数
        string filename = tmp.substr(0, tmp.find(' '));//文件名
        string line = tmp.substr(tmp.find(' ') + 1);//行号
        //cout<<filename<<endl<<num;
        if (filename.size() > 16)
            //取最后16个字符
            filename = filename.substr(filename.size() - 16);
        //插入之前判断信息是否已经存在容器中
        bool exist = false;
        for (auto& it : e_vec)//注意要用引用才能真实修改到容器中的数据
        {
            if (it.m_name == filename && it.m_line == line)
            {
                it.m_count++;
                exist = true;
                break;//找到则退出
            }
        }
        if (!exist)//不存在则插入容器
        {
            err info;//插入新的报错信息
            info.m_name = filename;
            info.m_line = line;
            info.m_count = 1;
            e_vec.push_back(info);
        }
    }
    //输出最后的八条记录
    int size = e_vec.size();
    for (int i = size>8 ? size-8 : 0 ; i < e_vec.size(); i++)
    {
        cout << e_vec[i].m_name << ' ' << e_vec[i].m_line << ' '
            << e_vec[i].m_count << endl;
    }
}