思路:ios
設tx爲t類別字符的個數。spa
①對於長度小於2的t明顯是"YES"
②對於字符類別只有1個的t明顯是"YES"
③對於字符類別有2個的t,如左上圖:若是str[l] != str[r],那麼咱們構造的t也應該是str[l] != str[r],且s字串和t的str[l]和str[r]是相反的,即如圖所示。繼續,如圖構造,即bbb..a...a這樣,咱們發現第一個圖片除去str[l] = a和str[r]=b以外,中間怎麼放置字符,都會出現"Irreducible Anagrams"的狀況,因此"YES"。
④對於字符類別有2個的t,若是str[l] == str[r],如右邊的圖,總有k = 2,讓s1包含一個a和bx個b,s2包含剩餘的ay個a使得知足"reducible Anagrams",因此"NO"。
④對於字符類別有3個的t,按着左上的圖也沒法構造出"Irreducible Anagrams" 狀況,說明字符類別爲3的t,說明不論字符排列都存在"reducible Anagrams",因此"NO"。
⑤對於字符類別大於3個的t,由④推出是"NO"。3d
#include <iostream> #include <cstdio> #include <algorithm> #include <cstring> using namespace std; const int N = 2e5 + 10; int dp[30][N]; char str[N]; void solve() { scanf("%s", str); int n = strlen(str); for(int i = 1; i <= n; ++i) { dp[str[i - 1] - 'a'][i]++; for(int c = 0; c < 26; ++c) { dp[c][i] += dp[c][i - 1]; } } /* for(int c = 0; c < 26; ++c) { printf("%c :\n", 'a' + c); for(int i = 1; i <= n; ++i) { printf("%d ", dp[c][i]); } printf("\n"); } */ int q; scanf("%d", &q); vector<pair<int ,int > > vp; for(int i = 0; i < q; ++i) { int l, r; scanf("%d%d", &l, &r); vp.push_back(make_pair(l, r)); } ///vector<int > ans; for(auto info : vp) { int l = info.first; int r = info.second; int kinds = 0; int sum = 0; for(int c = 0; c < 26; ++c) { kinds += (dp[c][r] - dp[c][l - 1]) > 0; sum += dp[c][r] - dp[c][l - 1]; } ///cout << "tot = " << kinds << endl; if(sum == 1 || (kinds == 2 && str[l - 1] != str[r - 1]) || kinds > 2) { printf("YES\n"); } else printf("NO\n"); } } int main() { solve(); return 0; }