poj 2531 分权问题 dfs算法

题意:一个集合(矩阵) m[i][j]=m[j][i]权值,分成两个集合,使其权值最大。注:在同一个集合中权值只能算一个。

思路:dfs

  1. 假设都在集合0
  2. 遍历 id 的时候拿到集合1
  3. 如果与 id 相关的在集合 0 整体权值要加 否则整体权值要减
  4. 如果拿到集合 1 权值变大了,继续向后dfs,然后接着一个回溯的操作

代码上需要注意的问题:

for (int i = id + 1; i < n; i++)
    {
        if (tmp > data)
        {
            dfs(i, tmp);
            dep[i] = 0;
        }
    }

这里有个回溯的操作,如果不执行dfs的话,就说明i放到集合1并不合适,所以放到集合0

解决问题的代码:

#include <iostream>
#include <cstdio>
#include <string.h>
using namespace std;
int map[30][30];
int dep[30];
int n, ans;
void dfs(int id, int data)
{
    dep[id] = 1;
    int tmp = data;
    for (int i = 0; i < n; i++)
    {
        if (dep[i] == 0) tmp += map[i][id];
        else tmp -= map[i][id];
    }
    if (ans < tmp) ans = tmp;
    for (int i = id + 1; i < n; i++)
    {
        if (tmp > data)
        {
            dfs(i, tmp);
            dep[i] = 0;
        }
    }
}
int main()
{
    scanf("%d", &n);
    for (int i = 0; i < n; i++)
        for (int j = 0; j < n; j++)
            scanf("%d", &map[i][j]);
    memset(dep, 0, sizeof(dep));
    ans = 0;
    dfs(0, 0);
    printf("%d\n", ans);
    return 0;
}

原文地址:https://www.cnblogs.com/xuxiaojin/p/9405672.html

时间: 2024-10-31 12:27:21

poj 2531 分权问题 dfs算法的相关文章

poj 2531 Network Saboteur (dfs)

Network Saboteur Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 9364   Accepted: 4417 Description A university network is composed of N computers. System administrators gathered information on the traffic between nodes, and carefully di

POJ 2531 Network Saboteur(dfs)

题目代号:POJ 2531 题目链接:http://poj.org/problem?id=2531 Language: Default Network Saboteur Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 13290   Accepted: 6428 Description A university network is composed of N computers. System administrator

poj 2531 Network Saboteur 解题报告

题目链接:http://poj.org/problem?id=2531 题目意思:将 n 个点分成两个部分A和B(也就是两个子集啦), 使得子集和最大(一定很难理解吧,呵呵).举个例子吧,对于样例,最佳的分法就是把点2分为一个子集,另一个子集理所当然就是1.3了. 2-1 的权值是50,2-3的权值是40,那么最大就是50+40 = 90了. 首先dfs的话,我不太会做啦.看了队长的用了状态压缩来做,一下子觉得好神奇!!!! 可能第一次接触,理解得不是太深刻,先留着吧.就觉得好神奇,好神奇...

poj 2531 -- Network Saboteur

Network Saboteur Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 9183   Accepted: 4313 Description A university network is composed of N computers. System administrators gathered information on the traffic between nodes, and carefully di

poj 2531 搜索剪枝

Network Saboteur Time Limit: 2000 MS Memory Limit: 65536 KB 64-bit integer IO format: %I64d , %I64u Java class name: Main [Submit] [Status] [Discuss] Description A university network is composed of N computers. System administrators gathered informat

【POJ 2531】Network Saboteur

[POJ 2531]Network Saboteur 图的搜索 剪枝真是门学问..剪好了快的可真不是一倍两倍 刚开始搜的思路有问题 TLE了 后来枚举点暴力搜了一发 两百多ms 由于查找时权值是不断增加的 所以直接找集合间最大权的话不方便设置return点 看disscuss发现有一大牛 建了两个数组 通过所有边权-两集合内部边权(去重) 得到答案 dfs的时候找最小内部边权即可 当前状态权值>当前最小内部边权时直接跳出 两个数组分别寸当前状态两个集合中所含的点 每加一个点分别往两边加 假设要将

POJ 1699 Best Sequence (DFS+预处理)

题意:看那张图就一清二楚了吧, N个序列首位相连(相同的序列部分),得到最短的总序列. 题目链接:http://poj.org/problem?id=1699 ~~~~ 思路就是:将N个序列首尾相连能重合的长度求粗来.然后DFS枚举每种首尾相连的情况. #include<cstdio> #include<cstring> #include<algorithm> #define N 22 #define INF 0x7fffffff using namespace std

POJ 3318 Matrix Multiplication(随机化算法)

给你三个矩阵A,B,C.让你判断A*B是否等于C. 随机一组数据,然后判断乘以A,B之后是否与乘C之后相等. 很扯淡的啊,感觉这种算法不严谨啊... Matrix Multiplication Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 16255   Accepted: 3515 Description You are given three n × n matrices A, B and C. Does the e

POJ 3411 Paid Roads(dfs)

*注:这一题很重要的是对与数据的处理和细节的把握把! http://poj.org/problem?id=3411 题目大意: 有n个城市,m条路,(0<=n,m<=10).从a到b,如果之前已经经过c点,那么付费p,否者付费r.求最小的费用,从1-->n! 注意: There may be more than one road connecting one city with another. so:你不能用map[a][b]存a->b的距离.只能有road [ i ]了. 还有