QOJ.ac

QOJ

IDSubmission IDProblemHackerOwnerResultSubmit timeJudge time
#502#286384#7743. Grand FinaleTsReaperTsReaperFailed.2023-12-17 19:39:442023-12-17 19:39:44

Details

Extra Test:

Accepted
time: 1ms
memory: 3752kb

input:

1
3 5
GWB
QWBQB

output:

3

result:

ok single line: '3'

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#286384#7743. Grand FinaleTsReaperAC ✓378ms77184kbC++172.7kb2023-12-17 19:39:092023-12-17 19:39:10

answer

#include <bits/stdc++.h>
#define MAXN 2500
#define MAXM 2500
#define INF ((int) 1e9)
using namespace std;
typedef pair<int, int> pii;

int n, m, ans;
char hand[MAXN + 10], pile[MAXM + 10];

int cntQ[MAXM + 10], cntB[MAXM + 10];

bool vis[MAXN + MAXM + 10][MAXN + MAXM + 10];
int f[MAXM + 10][MAXN + MAXM + 10];

void bfs() {
    queue<pii> q;
    for (int i = 0; i <= n + m; i++) for (int j = 0; j <= n + m; j++) vis[i][j] = false;
    q.push(pii(0, 0)); vis[0][0] = true;

    while (!q.empty()) {
        pii p = q.front(); q.pop();
        int pos = p.first + 2 * p.second;
        if (pos >= m) continue;
        int numQ = cntQ[pos] - p.first, numB = cntB[pos] - p.second;

        if (numQ > 0) {
            int ii = p.first + 1, jj = p.second;
            if (!vis[ii][jj]) {
                q.push(pii(ii, jj));
                vis[ii][jj] = true;
            }
        }
        if (numB > 0) {
            int ii = p.first, jj = p.second + 1;
            if (!vis[ii][jj]) {
                q.push(pii(ii, jj));
                vis[ii][jj] = true;
            }
        }
    }
}

void solve() {
    scanf("%d%d%s%s", &n, &m, hand + 1, pile + 1);
    
    cntQ[0] = cntB[0] = 0;
    for (int i = 1; i <= n; i++) {
        if (hand[i] == 'Q') cntQ[0]++;
        else if (hand[i] == 'B') cntB[0]++;
    }
    for (int i = 1; i <= m; i++) {
        cntQ[i] = cntQ[i - 1];
        cntB[i] = cntB[i - 1];
        if (pile[i] == 'Q') cntQ[i]++;
        else if (pile[i] == 'B') cntB[i]++;
    }
    bfs();

    for (int j = 0; j <= n + m; j++) f[m][j] = 0;
    for (int i = m - 1; i >= 0; i--) for (int j = 0; j <= n + m; j++) {
        f[i][j] = INF;
        
        if (j) {
            if (pile[i + 1] == 'Q') f[i][j] = min(f[i][j], f[i + 1][j]);
            else if (pile[i + 1] == 'B') f[i][j] = min(f[i][j], max(f[i + 1][j - 1] - 1, 0));
            else f[i][j] = min(f[i][j], f[i + 1][j - 1]);
        }

        int ii = min(i + 2, m);
        if (pile[i + 1] == 'Q') f[i][j] = min(f[i][j], f[ii][j + 1] + 1);
        else if (pile[i + 1] == 'B') f[i][j] = min(f[i][j], max(f[ii][j], 1));
        else f[i][j] = min(f[i][j], f[ii][j] + 1);
    }

    ans = INF;
    for (int i = 0; i <= cntQ[m]; i++) for (int j = 0; j <= cntB[m]; j++) if (vis[i][j]) {
        int pos = i + j * 2;
        if (pos >= m) ans = min(ans, n + m - i - j);
        else {
            int numQ = cntQ[pos] - i, numB = cntB[pos] - j;
            if (f[pos][numQ] <= numB) ans = min(ans, n + pos - i - j);
        }
    }
    if (ans == INF) printf("IMPOSSIBLE\n");
    else printf("%d\n", ans);
}

int main() {
    int tcase; scanf("%d", &tcase);
    while (tcase--) solve();
    return 0;
}