P6482 [CRCI2006-2007] CIRCLE

· · 题解

建议此题评蓝。

博客食用更佳

前置芝士 1:最小表示法

前置芝士 2\texttt{set}

前置芝士 3\texttt{dfs}

\texttt{update: 2020/12/31 增加了关于倒推时的说明}

\texttt{Step 0 题意}

\texttt{Step 1 正解}

时间复杂度:\mathcal{O}(2^kn^2k)

\texttt{Step 2 代码}

#include <cstdio>
#include <iostream>
#include <cstring>
#include <set>

using namespace std;

string Min (string x, string y) {return x < y ? x : y;}

int n, k;
string s, target;

set<string> S;

string get (string s) {
    string ret;
    ret = s;
    for (int i = 1; i < n; i++) {
        string tot = ret;
        int cnt = 0;
        for (int j = i; j < n; j++)
            tot[cnt++] = s[j];
        for (int j = 0; j < i; j++)
            tot[cnt++] = s[j];
        ret = Min(ret, tot);
    }
//  cout << s << " " << ret << endl;
//  cout << s << endl;
//  cout << ret << endl;
    return ret;
}

char change (char c) {return c == 'B' ? 'W' : 'B';}

void dfs (int x, string tot) {
    if (x == k) {
        S.insert(get(tot));
        return;
    }
    string t = tot;
    tot[0] = 'B';
    for (int i = 1; i < n; i++) {
        if (t[i - 1] == 'B')
            tot[i] = tot[i - 1];
        else
            tot[i] = change(tot[i - 1]);
    }
    if ((tot[n - 1] == tot[0] && t[n - 1] == 'B') || (tot[n - 1] != tot[0] && t[n - 1] == 'W'))
        dfs(x + 1, tot);
    tot[0] = 'W';
    for (int i = 1; i < n; i++) {
        if (t[i - 1] == 'B')
            tot[i] = tot[i - 1];
        else
            tot[i] = change(tot[i - 1]);
    }
    if ((tot[n - 1] == tot[0] && t[n - 1] == 'B') || (tot[n - 1] != tot[0] && t[n - 1] == 'W'))
        dfs(x + 1, tot);
}

int main () {
    scanf("%d %d", &n, &k);
    cin >> s;
    target = s;
    for (int i = 1; i <= k; i++) {
        char t = target[0];
        for (int j = 0; j < n - 1; j++) {
            if (target[j] == target[j + 1])
                target[j] = 'B';
            else
                target[j] = 'W';
        }
        if (target[n - 1] == t)
            target[n - 1] = 'B';
        else
            target[n - 1] = 'W';
    }
//  cout << target;
    dfs(0, target);
    printf("%d", S.size());
    return 0;
}