// @EXPECTED_RESULTS@: TIME_LIMIT_EXCEEDED, WRONG_ANSWER #include #include #include #include using namespace std; // Returns indices of v. vector longest_increasing_subsequence(vector>& v) { // parent: indices into v. vector parent(v.size(), 0); map> max_len; max_len[0] = {-1, 0}; for(int i = 0; i < v.size(); ++i) { auto it = prev(max_len.lower_bound(v[i].second)); auto len = it->second.second + 1; auto p = it->second.first; parent[i] = p; max_len[v[i].second] = {i, len}; it = max_len.lower_bound(v[i].second + 1); while(it != max_len.end() && it->second.second <= len) { it = max_len.erase(it); } // cerr << "Index " << i << " element " << v[i].first << "," << v[i].second << " has len " // << len << " from parent " << p << endl; } // for(auto x : max_len) { // cerr << x.first << " => " << x.second.first << "," << x.second.second << endl; // } vector path; auto idx = prev(max_len.end())->second.first; while(idx >= 0) { path.push_back(idx); idx = parent[idx]; } std::reverse(begin(path), end(path)); return path; } int main() { int n; cin >> n; vector> v(n); for(int i = 1; i <= n; ++i) { v[i - 1].first = i; cin >> v[i - 1].second; } int cx = 1, cy = 1; int steps = 0; auto move = [&](int x, int y) { steps += abs(x - cx); steps += abs(y - cy); cout << x << " " << y << "\n"; cx = x; cy = y; }; bool rev = false; bool dec = false; while(!v.empty()) { // lis step auto lis = longest_increasing_subsequence(v); reverse(begin(v), end(v)); auto lds = longest_increasing_subsequence(v); if(dec) { dec = !(lis.size() > 2 * lds.size()); } else { dec = lds.size() > 2 * lis.size(); } if(dec) { // cerr << "DEC SIZE: " << lds.size() << endl; if(rev) { reverse(begin(lis), end(lis)); } for(auto idx : lis) { move(v[idx].first, v[idx].second); } if(rev) { reverse(begin(lis), end(lis)); } for(auto it = lis.rbegin(); it != lis.rend(); ++it) { v.erase(v.begin() + *it); } reverse(begin(v), end(v)); } else { reverse(begin(v), end(v)); // cerr << "INC SIZE: " << lis.size() << endl; if(rev) { reverse(begin(lis), end(lis)); } for(auto idx : lis) { move(v[idx].first, v[idx].second); } if(rev) { reverse(begin(lis), end(lis)); } for(auto it = lis.rbegin(); it != lis.rend(); ++it) { v.erase(v.begin() + *it); } } rev = !rev; } }