1039 AlvinZH的学霸养成记IV

思路

难题,最大二分图匹配。

难点在于如何转化问题,n对n,一个只能攻击一个,判断是否存在一种攻击方案我方不死团灭对方。可以想到把所有随从看作点,对于可攻击的两个随从间连上边,这样就把问题转化为图了。

需要注意的是属性值的转化:免疫可看做生命值无限,剧毒可看做攻击力无限。(需要一点小小的机智)

图建好了,接下来怎么办呢?假设存在一种方案满足题意,那就是每个我方随从都可以找到敌方随从攻击,由于要团灭,只能存在一对一的情况,不存在多对一或一对多。如何表达这个方案呢?边!没错,就是刚才连起来的边的一个子集。这个子集有一个特点:n对n,n条边,边连着两边,且没有公共顶点。

没错,经过一番分析,最大二分图匹配已经很明显了。求解过程套板子就好了。

分析

二分图匹配算法

1.匈牙利算法:其本质就是,有条件就上,没条件创造条件也要上。DFS与BFS都可,时间复杂度均为 \(O(V⋅E)\) 。实际对于稀疏图BFS更佳。

2.Hopcroft-Karp算法:匈牙利算法的改进版,每次寻找多条增广路径。时间复杂度可以到达 \(O(n^{0.5}*m)\) 。

3.Dinic算法:二分图匹配其实是一个最大流问题,Dinic是一种优化过的求解最大流算法。与朴素的FF算法(\(O(n*m^2)\))不同,其可以同时多路增广。求解二分图时,构建超级源点和超级汇点,匹配边权值为1,求最大流即可。理论最坏复杂度为 \(O(n^2m)\) ,稠密图时比匈牙利DFS快了不少。

参考博客:二分图;

匈牙利算法;

Hopcroft-Karp算法;

Dinic算法

参考代码(DFS)

//
// Created by AlvinZH on 2017/11/27.
// Copyright (c) AlvinZH. All rights reserved.
// #include <cstdio>
#include <cstring>
#include <vector>
#define MaxSize 1005
#define INF 0x3f3f3f3f
using namespace std; int n, ans;
vector<int> G[MaxSize];//记录可攻击的敌方随从
int match[MaxSize];//记录匹配点
int visit[MaxSize];//记录是否访问 struct minion {
int attack, life;
}A[MaxSize], B[MaxSize]; bool dfs(int x)//寻找增广路径
{
for (int i = 0; i < G[x].size(); ++i)
{
int to = G[x][i];
if(!visit[to])
{
visit[to] = 1;
if(!match[to] || dfs(match[to]))
{
match[to] = x;
return true;
}
}
}
return false;
} int MaxMatch()
{
ans = 0;
memset(match, 0, sizeof(match));
for (int i = 1; i <= n; ++i)
{
memset(visit, 0, sizeof(visit));//清空访问
if(dfs(i)) ans++;//从节点i尝试扩展
}
return ans;
} int main()
{
while(~scanf("%d", &n))
{
int a, l, p;
for (int i = 1; i <= n; ++i) {
scanf("%d %d %d", &a, &l, &p); switch (p) {
case 0:
A[i].attack = a; A[i].life = l; break;
case 1:
A[i].attack = a; A[i].life = INF; break;
case 2:
A[i].attack = INF; A[i].life = l; break;
case 3:
A[i].attack = INF; A[i].life = INF; break;
default:
break;
}
}
for (int i = 1; i <= n; ++i)
scanf("%d %d", &B[i].attack, &B[i].life);
for (int i = 1; i <= n; ++i)
G[i].clear(); for (int i = 1; i <= n; ++i) {
for (int j = 1; j <= n; ++j) {
if(A[i].attack >= B[j].life && A[i].life > B[j].attack)
G[i].push_back(j);
}
}
if(n == MaxMatch()) printf("YES\n");
else printf("NO\n");
}
}

2016级算法第五次上机-E.AlvinZH的学霸养成记IV的更多相关文章

  1. 2016级算法第五次上机-D.AlvinZH的学霸养成记III

    850 AlvinZH的学霸养成记III 思路 难题.概率DP. 第一种思考方式:直接DP dp[i]:从已经有i个学霸到所有人变成学霸的期望. 那么答案为dp[1],需要从后往前逆推.对于某一天,有 ...

  2. 2016级算法第六次上机-F.AlvinZH的学霸养成记VI

    1082 AlvinZH的学霸养成记VI 思路 难题,凸包. 分析问题,平面上给出两类点,问能否用一条直线将二者分离. 首先应该联想到这是一个凸包问题,分别计算两类点的凸包,如果存在符合题意的直线,那 ...

  3. 2016级算法第六次上机-D.AlvinZH的学霸养成记V

    1081 AlvinZH的学霸养成记V 思路 中等题,计算几何. 这是一个排序问题,按极角排序.可以转化为叉积的应用,对于点A和B,通过叉积可以判断角度大小,共线时再判断距离. 叉积的应用.OA × ...

  4. 2016级算法第六次上机-C.AlvinZH的学霸养成记II

    1032 AlvinZH的学霸养成记II 思路 中等题,贪心. 所有课程按照DDL的大小来排序. 维护一个当前时间curTime,初始为0. 遍历课程,curTime加上此课程持续时间d,如果这时cu ...

  5. 2016级算法第五次上机-F.ModricWang的水系法术

    1066 ModricWang的水系法术 思路 比较典型的最大流问题,需要注意的是,题目已经暗示(明示)了这里的边是双向的,在建图的时候需要加上反向边的容量值. 解决最大流问题的基本思路就是不断在残量 ...

  6. 2016级算法第五次上机-C.Bamboo和"Coco"

    1064 Bamboo和"Coco" 分析题意 每个亡灵至少一个花瓣,相邻的亡灵中思念值高的要获得的花瓣高(思念值相等是不需要花瓣一样多的).主要考贪心思路,为了使得花瓣总量最少, ...

  7. 2016级算法第五次上机-B.Bamboo&APTX4844魔发药水

    Bamboo&APTX4844魔发药水 题意 "于是,Bamboo耐着性子,看巫师从袖子里掏出 M 瓶时光泉水和 K 粒绿色能量.每瓶时光泉水重量为 c ,生发效果为 l:每粒绿色能 ...

  8. 2016级算法第五次上机-A.Beihang Collegiate Pronunciation Contest 2017

    1065 Beihang Collegiate Pronunciation Contest 2017 思路 在字符串中不断做匹配 找到一个匹配就输出 时间复杂度\(O(n)\) ps.模式串是定长的, ...

  9. 2016级算法第五次上机-G.ModricWang的撒币游戏

    1062 ModricWang的撒币游戏 思路 此题为2017年ACM-ICPC亚洲区域赛乌鲁木齐赛区的A题,现场94个队中有38个队做出此题.在这里作为满分以外的题,是为了让大家看一下外面一些题的风 ...

随机推荐

  1. javascript的Undefined,null区别

    //在javascript中null表示“什么都没有” ,是一个特殊的类型,表示一个空对象引用: var person = null; //值为null(空),但类型为对象 console.log(p ...

  2. p1501 [国家集训队]Tree II

    传送门 分析 lct板子题 单独维护一下加和乘的情况即可 维护方法和维护翻转差不多 代码 #include<iostream> #include<cstdio> #includ ...

  3. input框添加阴影效果

    .input:hover,.input:focus{ border:1px solid #85afe1; -webkit-box-shadow:inset 0 1px 1px rgba(0, 0, 0 ...

  4. linux 创建数据库

    mysql -uroot -pxxxxxx 1. 修改服务器的字符集 打开/etc/mysql/my.cnf,在[mysqld]后添加character-set-server=utf8 2. 查看my ...

  5. 36 有n个整数,使其前面各数顺序向后移n个位置,最后m个数变成最前面的m个数

    题目:有n个整数,使其前面各数顺序向后移n个位置,最后m个数变成最前面的m个数 public class _036ExchangeSite { public static void main(Stri ...

  6. TinyMCE3.x整合教程-Xproer.WordPaster

    版权所有 2009-2017 荆门泽优软件有限公司 保留所有权利 官方网站:http://www.ncmem.com/ 产品首页:http://www.ncmem.com/webplug/wordpa ...

  7. mybatis 存储过程调用

    接口 UserInfoMapper.java xml   UserInfoMapper.xml 如何关联 <?xml version="1.0" encoding=" ...

  8. Arch Linux 使用markdown

    Arch Linux 使用markdown pandoc 文档格式转换 pygments 代码高亮 markdown-mode.el 配置emacs pandoc 号称文件格式转换的瑞士军刀,这里主要 ...

  9. 20169202 2016-2017-2《TCP/IP协议攻击》实验总结--十一周

    APR缓存中毒(ARP cache poisoning) 实验原理 ARP缓存是ARP协议的重要组成部分.ARP协议运行的目标就是建立MAC地址和IP地址的映射,然后把这一映射关系保存在ARP缓存中, ...

  10. JavaScript执行顺序

    当JavaScript引擎解析脚本时,它会在预编译期对所有声明的变量和函数进行处理.所以,就会出现当JavaScript解释器执行下面脚本时不会报错: alert(a);                ...