板子库

最大流

const int MAXN = 10010, MAXM = 20010, INF = 1e9;
struct MaxFlow {
	int S, T, head[MAXN], cur[MAXN], dis[MAXN], cnt = 1;
	bool vis[MAXN];
	struct edge {int v, c, nxt;} e[MAXM * 2];
	void add(int u, int v, int c) {
		e[++cnt] = {v, c, head[u]}, head[u] = cnt;
		e[++cnt] = {u, 0, head[v]}, head[v] = cnt;
	}
	void rebuild() {
		for (int i = 2; i <= cnt; i += 2)
			e[i].c += e[i ^ 1].c, e[i ^ 1].c = 0;
	}
	void clear() {
		memset(head, 0, sizeof(head));
		cnt = 1;
	}
	bool bfs() {
		memset(dis, 0x3f, sizeof(dis));
		memset(vis, 0, sizeof(vis));
		memcpy(cur, head, sizeof(head));
		queue<int> q; q.push(S), vis[S] = 1, dis[S] = 0;
		while (!q.empty()) {
			int u = q.front(); q.pop();
			for (int i = head[u]; i; i = e[i].nxt) {
				if (!e[i].c || vis[e[i].v]) continue;
				dis[e[i].v] = dis[u] + 1, vis[e[i].v] = 1;
				q.push(e[i].v);
			}
		}
		return vis[T];
	}
	int dfs(int now, int flow) {
		if(now == T) return flow;
		int res = 0;
		for(int i = cur[now]; i && res < flow; i = e[i].nxt) {
			if(!e[i].c || dis[e[i].v] != dis[now] + 1) {
				cur[now] = e[i].nxt;
				continue;
			}
			int tmp = dfs(e[i].v, min(flow - res, e[i].c));
			e[i].c -= tmp, e[i ^ 1].c += tmp, res += tmp;
			if(res < flow) cur[now] = e[i].nxt;
		}
		return res;
	}
	int solve() {
		int ans = 0;
		while (bfs()) ans += dfs(S, INF);
		return ans;
	}
} G;

MCMF

const int MAXN = 10010, MAXM = 20010, INF = 1e9;
struct MCMF {
	int S, T, head[MAXN], cnt = 1;
	int dis[MAXN], pre[MAXN], pree[MAXN];
	bool in[MAXN];
	struct edge {int v, c, w, nxt;} e[MAXM * 2];
	void add(int u, int v, int c, int w) {
		e[++cnt] = {v, c, w, head[u]}, head[u] = cnt;
		e[++cnt] = {u, 0, -w, head[v]}, head[v] = cnt;
	}
	void rebuild() {
		for (int i = 1; i <= cnt; i += 2)
			e[i].c += e[i ^ 1].c, e[i ^ 1].c = 0;
	}
	void clear() {
		memset(head, 0, sizeof(head));
		cnt = 1;
	}
	bool SPFA() {
		memset(dis, 0x3f, sizeof(dis));
		queue<int> q; q.push(S), in[S] = 1, dis[S] = 0;
		while (!q.empty()) {
			int u = q.front(); q.pop(), in[u] = 0;
			for (int i = head[u]; i; i = e[i].nxt) {
				if (!e[i].c || dis[e[i].v] <= dis[u] + e[i].w) continue;
				dis[e[i].v] = dis[u] + e[i].w;
				pre[e[i].v] = u, pree[e[i].v] = i;
				if (!in[e[i].v]) in[e[i].v] = 1, q.push(e[i].v);
			}
		}
		return dis[T] <= INF;
	}
	pair<int, int> getpath() {
		int now = T, flow = INF, cost = 0;
		while (now != S) flow = min(flow, e[pree[now]].c), now = pre[now];
		now = T;
		while (now != S) {
			int tmp = pree[now]; now = pre[now];
			e[tmp].c -= flow, e[tmp ^ 1].c += flow;
			cost += flow * e[tmp].w;
		}
		return {flow, cost};
	}
	pair<int, int> solve() {
		pair<int, int> ans(0, 0);
		while (SPFA()) {
			auto tmp = getpath();
			ans.first += tmp.first, ans.second += tmp.second;
		}
		return ans;
	}
} G;

SAM

const int MAXN = 50010;
struct SAM {
	struct node {
		int nxt[26], fa, len;
	} t[MAXN];
	int cnt, lst, sz[MAXN], ind[MAXN];
	int dfn[MAXN], dep[MAXN], tot;
	int lg[MAXN], tr[20][MAXN];
	SAM() : cnt(1), lst(1), tot(0) {}
	void insert(int x) {
		int cur = ++cnt, p = lst;
		t[cur].len = t[lst].len + 1;
		for (; p && t[p].nxt[x] == 0; p = t[p].fa)
			t[p].nxt[x] = cur;
		int q = t[p].nxt[x];
		if (q == 0) t[cur].fa = 1;
		else if (t[q].len == t[p].len + 1) t[cur].fa = q;
		else {
			int r = ++cnt;
			t[r] = t[q], t[r].len = t[p].len + 1;
			for (; p && t[p].nxt[x] == q; p = t[p].fa)
				t[p].nxt[x] = r;
			t[q].fa = t[cur].fa = r;
		}
		sz[cur] = 1, lst = cur;
	}
	vector<int> e[MAXN];
	void dfs(int now, int ndep) {
		tr[0][dfn[now] = ++tot] = now, dep[now] = ndep;
		for (int v : e[now])
			dfs(v, ndep + 1), sz[now] += sz[v];
	}
	void build(string s) {
		lg[1] = 0;
		for (int i = 2; i < MAXN; i++)
			lg[i] = lg[i / 2] + 1;
		for (int i = 0; i < s.size(); i++)
			insert(s[i] - 'a'), ind[i] = lst;
		for (int i = 2; i <= cnt; i++)
			e[t[i].fa].push_back(i);
		dfs(1, 0);
		for (int i = 1; i <= lg[MAXN - 1]; i++) {
			int x = 1 << i;
			for (int j = 1; j + x - 1 <= tot; j++) {
				if (dep[tr[i - 1][j]] < dep[tr[i - 1][j + x / 2]])
					tr[i][j] = tr[i - 1][j];
				else tr[i][j] = tr[i - 1][j + x / 2];
			}
		}
	}
	int LCA(int x, int y) {
		if (x == y) return x;
		x = dfn[x], y = dfn[y];
		if (x > y) swap(x, y);
		int len = lg[y - (x++)];
		if (dep[tr[len][x]] < dep[tr[len][y - (1 << len) + 1]])
			return t[tr[len][x]].fa;
		return t[tr[len][y - (1 << len) + 1]].fa;
	}
	int LCS(int x, int y) {
		return t[LCA(ind[x], ind[y])].len;
	}
	void clear() {
		do {
			memset(t[cnt].nxt, 0, sizeof(t[cnt].nxt));
			t[cnt].fa = t[cnt].len = 0;
		} while (--cnt);
		cnt = lst = 1, tot = 0;
	}
} T;
posted @ 2023-03-15 15:55  曹轩鸣  阅读(75)  评论(0编辑  收藏  举报