e6ccb20270 2014-05-17 kinaba: #include <iostream> e6ccb20270 2014-05-17 kinaba: #include <sstream> e6ccb20270 2014-05-17 kinaba: #include <iomanip> e6ccb20270 2014-05-17 kinaba: #include <vector> e6ccb20270 2014-05-17 kinaba: #include <string> e6ccb20270 2014-05-17 kinaba: #include <map> e6ccb20270 2014-05-17 kinaba: #include <set> e6ccb20270 2014-05-17 kinaba: #include <algorithm> e6ccb20270 2014-05-17 kinaba: #include <numeric> e6ccb20270 2014-05-17 kinaba: #include <iterator> e6ccb20270 2014-05-17 kinaba: #include <functional> e6ccb20270 2014-05-17 kinaba: #include <complex> e6ccb20270 2014-05-17 kinaba: #include <queue> e6ccb20270 2014-05-17 kinaba: #include <stack> e6ccb20270 2014-05-17 kinaba: #include <cmath> e6ccb20270 2014-05-17 kinaba: #include <cassert> e6ccb20270 2014-05-17 kinaba: #include <tuple> e6ccb20270 2014-05-17 kinaba: using namespace std; e6ccb20270 2014-05-17 kinaba: typedef long long LL; e6ccb20270 2014-05-17 kinaba: typedef complex<double> CMP; e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: class CandidatesSelection { public: e6ccb20270 2014-05-17 kinaba: string possible(vector <string> score, vector <int> result) e6ccb20270 2014-05-17 kinaba: { e6ccb20270 2014-05-17 kinaba: return solve(score, result) ? "Possible" : "Impossible"; e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: bool solve(vector <string> score, vector <int> result) e6ccb20270 2014-05-17 kinaba: { e6ccb20270 2014-05-17 kinaba: const int N = score.size(); e6ccb20270 2014-05-17 kinaba: const int S = score[0].size(); e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: // po[a][b] : bitmask of skill set that makes a<b. e6ccb20270 2014-05-17 kinaba: vector<vector<LL>> po(N, vector<LL>(N)); e6ccb20270 2014-05-17 kinaba: for(int a=0; a<N; ++a) e6ccb20270 2014-05-17 kinaba: for(int b=0; b<N; ++b) if(a!=b) e6ccb20270 2014-05-17 kinaba: { e6ccb20270 2014-05-17 kinaba: LL mask = 0; e6ccb20270 2014-05-17 kinaba: for(int s=0; s<S; ++s) e6ccb20270 2014-05-17 kinaba: if(score[a][s] <= score[b][s]) e6ccb20270 2014-05-17 kinaba: mask |= 1LL<<s; e6ccb20270 2014-05-17 kinaba: if(a<b) e6ccb20270 2014-05-17 kinaba: mask |= 1LL<<S; e6ccb20270 2014-05-17 kinaba: po[a][b] = mask; e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: vector<vector<int>> now(1, result); e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: function<bool(LL,vector<vector<int>>)> rec; e6ccb20270 2014-05-17 kinaba: rec = [&](LL used, vector<vector<int>> obl) { e6ccb20270 2014-05-17 kinaba: LL pos = ~0LL; e6ccb20270 2014-05-17 kinaba: for(auto& oi: obl) e6ccb20270 2014-05-17 kinaba: for(int i=0; i+1<oi.size(); ++i) e6ccb20270 2014-05-17 kinaba: pos &= po[oi[i]][oi[i+1]]; e6ccb20270 2014-05-17 kinaba: if(pos & (1LL<<S)) // original order is enough. e6ccb20270 2014-05-17 kinaba: return true; e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: bool changed = false; e6ccb20270 2014-05-17 kinaba: for(int s=0; s<S; ++s) if(pos & ~used & (1LL<<s)) { e6ccb20270 2014-05-17 kinaba: vector<vector<int>> next; e6ccb20270 2014-05-17 kinaba: for(auto& oi: obl) { e6ccb20270 2014-05-17 kinaba: vector<int> cur; e6ccb20270 2014-05-17 kinaba: for(int o: oi) { e6ccb20270 2014-05-17 kinaba: if(!cur.empty() && score[cur.back()][s] < score[o][s]) { e6ccb20270 2014-05-17 kinaba: changed = true; e6ccb20270 2014-05-17 kinaba: if(cur.size()>=2) e6ccb20270 2014-05-17 kinaba: next.push_back(cur); e6ccb20270 2014-05-17 kinaba: cur.clear(); e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: cur.push_back(o); e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: if(cur.size()>=2) e6ccb20270 2014-05-17 kinaba: next.push_back(cur); e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: obl = std::move(next); e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: return changed && rec(used|pos, obl); e6ccb20270 2014-05-17 kinaba: }; e6ccb20270 2014-05-17 kinaba: return rec(0, now); e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: }; e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: // BEGIN CUT HERE e6ccb20270 2014-05-17 kinaba: #include <ctime> e6ccb20270 2014-05-17 kinaba: double start_time; string timer() e6ccb20270 2014-05-17 kinaba: { ostringstream os; os << " (" << int((clock()-start_time)/CLOCKS_PER_SEC*1000) << " msec)"; return os.str(); } e6ccb20270 2014-05-17 kinaba: template<typename T> ostream& operator<<(ostream& os, const vector<T>& v) e6ccb20270 2014-05-17 kinaba: { os << "{ "; e6ccb20270 2014-05-17 kinaba: for(typename vector<T>::const_iterator it=v.begin(); it!=v.end(); ++it) e6ccb20270 2014-05-17 kinaba: os << '\"' << *it << '\"' << (it+1==v.end() ? "" : ", "); os << " }"; return os; } e6ccb20270 2014-05-17 kinaba: void verify_case(const string& Expected, const string& Received) { e6ccb20270 2014-05-17 kinaba: bool ok = (Expected == Received); e6ccb20270 2014-05-17 kinaba: if(ok) cerr << "PASSED" << timer() << endl; else { cerr << "FAILED" << timer() << endl; e6ccb20270 2014-05-17 kinaba: cerr << "\to: \"" << Expected << '\"' << endl << "\tx: \"" << Received << '\"' << endl; } } e6ccb20270 2014-05-17 kinaba: #define CASE(N) {cerr << "Test Case #" << N << "..." << flush; start_time=clock(); e6ccb20270 2014-05-17 kinaba: #define END verify_case(_, CandidatesSelection().possible(score, result));} e6ccb20270 2014-05-17 kinaba: int main(){ e6ccb20270 2014-05-17 kinaba: e6ccb20270 2014-05-17 kinaba: CASE(0) e6ccb20270 2014-05-17 kinaba: string score_[] = {"CC", "AA", "BB"}; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = {1,2,0}; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = "Possible"; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: CASE(1) e6ccb20270 2014-05-17 kinaba: string score_[] = {"BAB", "ABB", "AAB", "ABA"}; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = {2,0,1,3}; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = "Possible"; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: CASE(2) e6ccb20270 2014-05-17 kinaba: string score_[] = {"BAB", "ABB", "AAB", "ABA"}; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = {0, 1, 3, 2}; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = "Impossible"; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: CASE(3) e6ccb20270 2014-05-17 kinaba: string score_[] = {"AAA", "ZZZ"}; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = {1, 0}; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = "Impossible"; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: CASE(4) e6ccb20270 2014-05-17 kinaba: string score_[] = {"ZZZ", "AAA"}; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = {0, 1}; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = "Possible"; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: CASE(5) e6ccb20270 2014-05-17 kinaba: string score_[] = {"ZYYYYX","YXZYXY","ZZZZXX","XZXYYX","ZZZYYZ","ZZXXYZ","ZYZZXZ","XZYYZX"}; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = {3,7,1,0,2,5,6,4}; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = "Possible"; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: /* e6ccb20270 2014-05-17 kinaba: CASE(6) e6ccb20270 2014-05-17 kinaba: string score_[] = ; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = ; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = ; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: CASE(7) e6ccb20270 2014-05-17 kinaba: string score_[] = ; e6ccb20270 2014-05-17 kinaba: vector <string> score(score_, score_+sizeof(score_)/sizeof(*score_)); e6ccb20270 2014-05-17 kinaba: int result_[] = ; e6ccb20270 2014-05-17 kinaba: vector <int> result(result_, result_+sizeof(result_)/sizeof(*result_)); e6ccb20270 2014-05-17 kinaba: string _ = ; e6ccb20270 2014-05-17 kinaba: END e6ccb20270 2014-05-17 kinaba: */ e6ccb20270 2014-05-17 kinaba: } e6ccb20270 2014-05-17 kinaba: // END CUT HERE