WA求调,实在看不动了
查看原帖
WA求调,实在看不动了
678858
ShiRoZeTsuHL卜奎BBQ!楼主2023/9/22 08:24

样例是能过的,但是交在SPOJ上会WA,看不到数据就很难受

#include <iostream>
#include <cstdio>
#include <cstring>
#include <vector>
#include <queue>

const int maxn = 2e4 + 5;
const int maxs = 3e5 + 5;

int T, n, cur, ans, dfncnt;
int w[maxn], st[maxn], pos[maxn], dfn[maxs], sze[maxs];
char s[maxs];

struct edge {
    int to, nxt;
} e[maxs];

int tot = 1, head[maxs];
void addedge(int u, int v) {
    e[++tot].to = v;
    e[tot].nxt = head[u];
    head[u] = tot;
}

struct AcAutomaton {
    int trietot;
    int ch[maxs][26], fail[maxs];

    void ins(char* p, int id) {
        int len = strlen(p+1), now = 0;
        for(int i = 1; i <= len; i++) {
            int v = p[i]-'a';
            if(!ch[now][v]) ch[now][v] = ++trietot;
            now = ch[now][v];
        }
        pos[id] = now;
    }

    void build() {
        std::queue<int> q;
        for(int i = 0; i < 26; i++)
            if(ch[0][i]) q.push(ch[0][i]), addedge(0, ch[0][i]);
        while(!q.empty()) {
            int u = q.front(); q.pop();
            for(int i = 0; i < 26; i++) {
                int v = ch[u][i];
                if(v) {
                    fail[v] = ch[fail[u]][i];
                    addedge(fail[v], v);
                    q.push(v);
                }
                else ch[u][i] = ch[fail[u]][i];
            }
        }
    }
} ac;

struct SegmentTree {
#define ls (id << 1)
#define rs (id << 1 | 1)
#define mid ((l + r) >> 1)

    int t[maxs<<2], lazy[maxn<<2];

    void pushdown(int id) {
        if(lazy[ls] < lazy[id]) {
            t[ls] = std::max(t[ls], lazy[id]);
            lazy[ls] = std::max(lazy[ls], lazy[id]);
        }
        if(lazy[rs] < lazy[id]) {
            t[rs] = std::max(t[rs], lazy[id]);
            lazy[rs] = std::max(lazy[rs], lazy[id]);
        }
        lazy[id] = 0;
    }

    void modify(int l, int r, int id, int ql, int qr, int val) {
        if(ql <= l && r <= qr) {
            t[id] = std::max(t[id], val);
            lazy[id] = std::max(lazy[id], val);
            return;
        }
        if(lazy[id] > val) return;
        if(lazy[id]) pushdown(id);
        if(ql <= mid) modify(l, mid, ls, ql, qr, val);
        if(mid < qr) modify(mid+1, r, rs, ql, qr, val);
        t[id] = std::max(t[ls], t[rs]);
    }

    int query(int l, int r, int id, int q) {
        if(l == r) return t[id];
        if(lazy[id]) pushdown(id);
        if(q <= mid) return query(l, mid, ls, q);
        else return query(mid+1, r, rs, q);
    }
} seg;

void dfs(int u) {
    dfn[u] = ++dfncnt;
    sze[u] = 1;
    for(int i = head[u]; i; i = e[i].nxt) {
        int v = e[i].to;
        dfs(v);
        sze[u] += sze[v];
    }
}

int getans(char* p) {
    int len = strlen(p+1), now = 0, res = 0;
    for(int i = 1; i <= len; i++) {
        int v = p[i]-'a';
        now = ac.ch[now][v];
        res = std::max(res, seg.query(1, dfncnt, 1, dfn[now]));
    }
    return res;
}

void clear() {
    cur = -1;
    ans = dfncnt = ac.trietot = 0;
    tot = 1;
    memset(head, 0, sizeof(head));
    memset(e, 0, sizeof(e));
    memset(ac.ch, 0, sizeof(ac.ch));
    memset(ac.fail, 0, sizeof(ac.fail));
    memset(seg.t, 0, sizeof(seg.t));
    memset(seg.lazy, 0, sizeof(seg.lazy));
}

int main() {
    scanf("%d", &T);
    for(int F = 1; F <= T; F++) {
        clear();

        scanf("%d", &n);
        for(int i = 1; i <= n; i++) {
            scanf("%s", s+cur+2);
            scanf("%d", &w[i]);
            st[i] = cur+1;
            ac.ins(s+cur+1, i);
            cur += strlen(s+cur+2) + 1;
        }

        ac.build();
        dfs(0);
        for(int i = 1; i <= n; i++) {
            int x = getans(s+st[i]) + w[i];
            seg.modify(1, dfncnt, 1, dfn[pos[i]], dfn[pos[i]]+sze[pos[i]]-1, x);
            ans = std::max(ans, x);
        }
        printf("Case #%d: %d\n", F, ans);
    }
    return 0;
}
2023/9/22 08:24
加载中...