代码求调 玄关
  • 板块P4142 洞穴遇险
  • 楼主luuia
  • 当前回复0
  • 已保存回复0
  • 发布时间2024/4/1 21:33
  • 上次更新2024/4/2 12:22:54
查看原帖
代码求调 玄关
557800
luuia楼主2024/4/1 21:33

rt.已经改的和题解差不多了还是只有70 后三个点WA

#include<bits/stdc++.h>
using namespace std;

long long read()
{
    long long s = 0,w = 1;
    char ch = getchar();
    while(ch < '0' || ch > '9')
    {
        if(ch == '-') w = -1;
        ch = getchar();
    }
    while(ch >= '0' && ch <= '9')
    {
        s = (s << 1) + (s << 3) + (ch ^ 48);
        ch = getchar();
    }
    return s * w;
}

void write(long long a)
{
    if(a > 9) write(a / 10);
    putchar(a % 10 + '0');
}

const long long N = 4e5 + 10,inf = 0x3f3f3f3f;
const long long dx[5] = {0,1,-1,0,0};
const long long dy[5] = {0,0,0,1,-1};
bool vis[N],can[110][110];
long long sum,a[110][110];
long long n,m,k,S,s,t,u,v,w,f,op,cost[N],pre[N],l[N],flow[N],maxflow,mincost;

struct EDGE{long long to,nxt,flow,cost;}e[N];

long long head[N],cnt;queue<long long> q;

void add(long long from,long long to,long long flow,long long cost)
{
	e[++cnt].nxt = head[from];e[cnt].to = to;e[cnt].flow = flow;e[cnt].cost = cost;head[from] = cnt;
    e[++cnt].nxt = head[to];e[cnt].to = from;e[cnt].flow = 0;e[cnt].cost = -cost;head[to] = cnt;
}

bool spfa(long long s,long long t)
{
	memset(cost,0x7f,sizeof(cost));memset(flow,0x7f,sizeof(flow));
	memset(vis,0,sizeof(vis));q.push(s),vis[s] = 1,cost[s] = 0,pre[t] = -1;
	while(q.size())
	{
		long long newn = q.front();q.pop(),vis[newn] = 0;
		for(long long i = head[newn];i != -1;i = e[i].nxt)
		{
			long long v = e[i].to;
			if(e[i].flow > 0 && cost[v] > cost[newn] + e[i].cost)
			{
				cost[v] = cost[newn] + e[i].cost;
				pre[v] = newn;l[v] = i;
				flow[v] = min(flow[newn],e[i].flow);
				if(!vis[v]){vis[v] = 1;q.push(v);}
			}
		}
	}
	return pre[t] != -1;
}

void mincost_maxflow()
{
	while(spfa(s,t))
	{
		long long newn = t;
		maxflow += flow[t];mincost += flow[t] * cost[t];
		while(newn != s)
		{
			e[l[newn]].flow -= flow[t];
			e[l[newn] ^ 1].flow += flow[t];newn = pre[newn];
		}
	}
}

void init(){memset(head,-1,sizeof(head));cnt = -1;}
long long num(long long x,long long y,long long z){return (x - 1) * n + y + z * n * n;}
bool check(long long x,long long y){return (x >= 1 && x <= n && y >= 1 && y <= n && !can[x][y]);}

int main()
{
	// freopen("input.in","r",stdin);
	init();
	n = read(),m = read(),k = read(),op = n * n;
    S = 1e5,t = S + 1,s = t + 1;
    for(long long i = 1;i <= n;i++){for(long long j = 1;j <= n;j++) a[i][j] = read(),sum += a[i][j];}
    for(long long i = 1;i <= k;i++){u = read(),v = read();can[u][v] = 1;}
    add(s,S,m,0);
    for(long long i = 1;i <= n;i++)
    {
        for(long long j = 1;j <= n;j++)
        {
            if((i + j) % 2 == 1)
            {
                add(num(i,j,2),num(i,j,3),1,-a[i][j]);
                for(long long k = 1;k <= 4;k++)
                {
                    long long xx = i + dx[k],yy = j + dy[k];
                    if(!check(xx,yy)) continue;
                    if(yy % 2 == 1) add(num(xx,yy,1),num(i,j,2),1,0);
                    else add(num(i,j,3),num(xx,yy,4),1,0);
                }
                continue;
            }
            if(j % 2 == 1) add(S,num(i,j,1),1,0);
            else add(num(i,j,4),t,1,0);
        }
    }
    mincost_maxflow();
    write(sum + mincost);
	return 0;
}
2024/4/1 21:33
加载中...