Hello Codeforces. Recently I solved problems from VKOSHP XXII on CF and found something weird.
I've got 2 solutions of problem I — Wheel of Fortune
1st solution:
#include<bits/stdc++.h>
using namespace std;
const int N = 1e5;
string s[N + 10];
bool recur(vector<int> positions, set<char> letters) {
int m = (int)positions.size();
if(m == 1)
return 1;
set<char> oldl = letters;
for(int i = 0;i < m;i++) {
set<char> newl;
for(char c : s[ positions[ i ] ]) {
if(letters.count( c ))
newl.insert(c);
}
letters = newl;
}
if(letters.empty()) return 0;
char letter = *letters.begin();
unordered_map<string, vector<int>> mp;
for(int i = 0;i < m;i++) {
string pt = "";
for(char c : s[ positions[ i ] ]) {
pt += (c == letter ? letter : '#');
}
mp[ pt ].push_back( positions[ i ] );
}
oldl.erase(letter);
for(auto c : mp) {
if(!recur(c.second, oldl)) return 0;
}
return 1;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0);cout.tie(0);
int l, n;
cin >> l >> n;
vector<int> pos(n);
set<char> letters;
for(int i = 0;i < n;i++) {
cin >> s[ i ];
pos[ i ] = i;
}
for(char c = 'a';c <= 'z';c++)
letters.insert(c);
cout << (recur(pos, letters) ? "YES" : "NO");
}
and 2nd:
#include<bits/stdc++.h>
using namespace std;
const int N = 1e5;
string s[N + 10];
string words[N + 10]; // <== new line
bool recur(vector<int> positions, set<char> letters) {
int m = (int)positions.size();
if(m == 1)
return 1;
set<char> oldl = letters;
for(int i = 0;i < m;i++) {
words[ i ] = s[ positions[ i ] ]; // <== new line
set<char> newl;
for(char c : s[ positions[ i ] ]) {
if(letters.count( c ))
newl.insert(c);
}
letters = newl;
}
if(letters.empty()) return 0;
char letter = *letters.begin();
unordered_map<string, vector<int>> mp;
for(int i = 0;i < m;i++) {
string pt = "";
for(char c : s[ positions[ i ] ]) {
pt += (c == letter ? letter : '#');
}
mp[ pt ].push_back( positions[ i ] );
}
oldl.erase(letter);
for(auto c : mp) {
if(!recur(c.second, oldl)) return 0;
}
return 1;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0);cout.tie(0);
int l, n;
cin >> l >> n;
vector<int> pos(n);
set<char> letters;
for(int i = 0;i < n;i++) {
cin >> s[ i ];
pos[ i ] = i;
}
for(char c = 'a';c <= 'z';c++)
letters.insert(c);
cout << (recur(pos, letters) ? "YES" : "NO");
}
1st solution gives TLE on test 52, but in solution 2 I just added an array words which I'm not using at all but it gets AC (P.S. in 2nd code I marked the lines which aren't in 1st one).
So here in confusion I asking anybody explain me the reason of this jump in execution time of my code








Hell if I know...
Compiled in godbolt (https://godbolt.org/z/ez9bvr1j7)
See diff (https://www.diffchecker.com/KIuntEa5)
It's really huge, seems like after both
recurandmainfunctions end there happening some massive stuff (like creation strings and removing unordered maps).P.S. I don't like stuff like copying objects in recursive methods, and I don't know about your algorithm and can't read assembler (yeah, I don't know shit:)), but the only hypothesis I can came up is really unobvious optimizations in that part (like not copying objects in recurring)