問題URL : https://www.hackerrank.com/challenges/attribute-parser/problem
-
getlineで行ごと取得したあと、cin >> wsで改行文字を捨てる。
https://qiita.com/iseki-masaya/items/70b4ee6e0877d12dafa8 を見ながら文字列split用の関数を作成 -
文字列に、tag1.tag2.tag3...のように、開始のtagが出てくるたびに追加し、</tag?>が出るたびにtag?を削除していく。そのように作った文字列をキーにして、Valueを、キーを要素、Valueを値(string)にしたmapとした。
-
テストケースの中に「<tag6>¥n」 みたいな行があり、処理できずにsegmentation fault(Abort Call)になった。低能なのでメモリの使いすぎと思ってresizeやvector,mapのメモリ解放を試したり、continueを入れ忘れたりした。解決するのに1日かかった。
#include <cmath>
#include <cstdio>
#include <vector>
#include <iostream>
#include <algorithm>
#include <sstream>
#include <map>
#include <sstream>
#include <unordered_map>
using namespace std;
vector<string> Split(const string &s,char delim){
vector<string> elem(100);
stringstream ss(s);
string item;
int i=0;
while(getline(ss,item,delim)){
if(!item.empty()){
elem[i]=item;
}else{
break;
}
i++;
}
elem.resize(i);
return elem;
}
template<typename K, typename V>
void print_map(unordered_map<K,V> const &m)
{
for (auto const& pair: m) {
std::cout << "{" << pair.first << ": " << pair.second << "}\n";
}
}
template<typename K, typename V>
void print_vector(vector<K,V> v){
for(int i=0;i<v.size();i++){
cout << v[i] << " ";
}
cout << endl;
}
unordered_map<string,unordered_map<string,string>> M;
void make_elem_map(int n){
unordered_map<string,string> mtemp;
vector<string> str;
string m_key="";
string s,value;
for(int i=0;i<n;i++){
getline(cin,s);
cin >> ws;
// printf("%d getline is ok s:%s\n",i,s.c_str());
if(s[1]!='/'){
str=Split(s,' ');
// printf("%d str.size():%u\n",i,str.size());
if(str.size()==1){
string tag=str[0].erase(0,1).erase(str[0].length()-1,1);
if(m_key.size()==0)m_key+=tag;
else m_key+=("."+tag);
continue;
}
for(int j=1;j<str.size()-2;j+=3){
value=str[j+2];
value.erase(0,1);
if(j==str.size()-3)value.erase(value.length()-2,2);
else value.erase(value.length()-1,1);
mtemp.insert(make_pair(str[j],value));
}
string tag=str[0].erase(0,1);
if(m_key.size()==0)m_key+=tag;
else m_key+=("."+tag);
M.insert(make_pair(m_key,mtemp));
mtemp.clear();
str.clear();
}else{
string tag=s.erase(0,2).erase(s.length()-1,1);
if(m_key.length()>tag.length())m_key.erase(m_key.find("."+tag), tag.length()+1);
else m_key.clear();
}
// printf("%d is ok\n",i);
}
str.clear();
str.shrink_to_fit();
m_key.clear();
m_key.shrink_to_fit();
}
int main() {
/* Enter your code here. Read input from STDIN. Print output to STDOUT */
int n,q;
cin >> n >> q;
cin >> ws;
make_elem_map(n);
// int cnt=0;
// if(M.empty())printf("M is empty!\n");
// else printf("M is not empty!\n");
// for(auto const& pair: M){
// cout << cnt << endl << "parent key: " << pair.first << endl;
// // print_vector(pair.first);
// printf("value_map key,value: ");
// print_map(pair.second);
// cnt++;
// }
vector<string> query;
string s;
for(int i=0;i<q;i++){
getline(cin,s);
cin >> ws;
query=Split(s,'~');
if(M[query[0]].count(query[1])!=0)printf("%s\n",M[query[0]][query[1]].c_str());
else printf("Not Found!\n");
}
return 0;
}