【金牌导航】【洛谷 P3201】【启发式合并】梦幻布丁

题目



解题思路

启发式合并真的就是想到挺难的,想到后简单得很
如何判断有几段还是很容易的,如果和前一个布丁颜色不同,段数+1
将每一种颜色看作一条链
改变颜色可以看作将两条链合并
为了时间更优,肯定是要将数量少的合并到多的
所以要记录原来的颜色x当前是颜色b[x]
如果改颜色后与前面或后面颜色相同,段数-1
合并后要及时更新颜色的数量


代码

#include<iostream>
#include<cstdio>
using namespace std;
int n,m,q,x,y,ans,a[100010],b[1000010],f[100010];
int cnt[1000010],head[1000010];
int main()
{scanf("%d%d",&n,&m);for (int i=1;i<=n;i++){ scanf("%d",&a[i]);b[a[i]]=a[i];  //当前颜色没变 cnt[a[i]]++;f[i]=head[a[i]];  //上一个同颜色的 head[a[i]]=i;  //此颜色最后一个的位置 if (a[i]!=a[i-1]) ans++;}while (m--){scanf("%d",&q);if (q==2){printf("%d\n",ans);continue;}int j=0;scanf("%d%d",&x,&y);if (x==y) continue;     if (cnt[b[x]]>cnt[b[y]]) swap(b[x],b[y]);  //将数量少的合并到多的,改变颜色  x=b[x],y=b[y];for (int i=head[x];i;i=f[i]){if (a[i-1]==y) ans--;if (a[i+1]==y) ans--;}for (int i=head[x];i;i=f[i]) a[j=i]=y;if (head[x]) {f[j]=head[y],head[y]=head[x];cnt[y]+=cnt[x],head[x]=cnt[x]=0;  //合并后更新数量,改变链头 }}return 0;
}

【金牌导航】【洛谷 P3201】【启发式合并】梦幻布丁相关推荐

  1. 贪心算法——洛谷(P1090)[NOIP2004]合并果子

    该题目也属于经典的贪心算法,在这里熟悉C++里优先队列的使用. 需要导入头文件:   #include<queue> 从这个问题可以深挖出神奇的哈夫曼树问题. 因为这题里合并的是二叉树,所 ...

  2. 【洛谷1090】合并果子

    题目描述 在一个果园里,多多已经将所有的果子打了下来,而且按果子的不同种类分成了不同的堆.多多决定把所有的果子合成一堆. 每一次合并,多多可以把两堆果子合并到一起,消耗的体力等于两堆果子的重量之和.可 ...

  3. 洛谷 P1631 序列合并

    嗯... 题目链接:https://www.luogu.org/problem/P1631 这道题很明显的是一个堆的问题,要开一个结构体的堆(结构体中记录下标.内容.个数)... 首先,把A和B两个序 ...

  4. 洛谷P1775 石子合并(弱化版)

    原题传送门 题目描述 设有 N(N≤300)N(N \le 300)N(N≤300) 堆石子排成一排,其编号为1,2,3,⋯,N1,2,3,\cdots,N1,2,3,⋯,N.每堆石子有一定的质量 m ...

  5. [优先队列] 洛谷 P1631 序列合并

    题目描述 有两个长度都是N的序列A和B,在A和B中各取一个数相加可以得到N^2N2个和,求这N^2N2个和中最小的N个. 输入输出格式 输入格式: 第一行一个正整数N: 第二行N个整数A_iAi​, ...

  6. 洛谷 深基 第4部分 基础数学与数论(19-21课)

    洛谷 深基 第4部分 基础数学与数论  第19章 位运算与进制转换 P1143 进制转换 https://www.luogu.com.cn/problem/P1143 洛谷P1143 进制转换的Pyt ...

  7. 【启发式合并】梦幻布丁(金牌导航 启发式合并-1/luogu 3201)

    梦幻布丁 金牌导航 启发式合并-1 luogu 3201 题目大意 有若干个布丁,给出它们的颜色,每次将一个颜色的所有布丁变成另一种颜色,然后询问有多少段连续的数 输入样例 4 3 1 2 2 1 2 ...

  8. P3201 [HNOI2009]梦幻布丁 [启发式合并][set]

    P3201 [HNOI2009]梦幻布丁 题意:N个布丁摆成一行,进行M次操作.每次将某个颜色的布丁全部变成另一种颜色的,然后再询问当前一共有多少段颜色.例如颜色分别为1,2,2,1的四个布丁一共有3 ...

  9. P3201 [HNOI2009] 梦幻布丁 启发式合并

    P3201 [HNOI2009] 梦幻布丁 考察:启发式合并,set 思路: 这种不可逆的改变都应该采用启发式合并,即把集合大小小的合并到大的去.那么要统计cnt,遍历小的集合中的每个元素,它前面的那 ...

最新文章

  1. 直方图中最大的矩形(遍历与单调栈)
  2. mysql5.6 临时表_MySQL5.6 运用临时表做SQL优化
  3. for each....in、for in、for of
  4. JS高级:事件冒泡和事件捕获;
  5. ReentrantLock可重入锁使用及原理
  6. 自学python怎么转行_没有基础的想转行学习Python怎么学
  7. redis3.0伪集群安装步骤
  8. lua 给userdata设置元表_提高Lua语言开发效率的简单方法
  9. Linux如何切换图形界面和命令行界面
  10. grafana的前端技术_Grafana开发环境搭建
  11. 用友u8采购发票如何取消审核
  12. 《阿甘正传》,看了很多遍,是否留意到这个镜头???
  13. E - Elevator
  14. SuperMap iClient3D for WebGL 示范案例(一)倾斜模型加载
  15. linux通过usb给windows,如何从Linux创建Windows USB安装程序 | MOS86
  16. Android Studio模拟器安装步骤
  17. Java23种设计模式——2.创建型模式之原型模式
  18. 5-3 人际资源整合-辨别同事、结交优质同事、拒绝烂同事
  19. python画circos图_Circos图--在线绘制
  20. 计算机与科学技术专业毕业设计,计算机科学与技术专业毕业设计论文

热门文章

  1. 2738 小鑫の日常系列故事(七)——小纸条
  2. VirtualBox提示:错误,创建一个新任务失败,被召者解决办法
  3. 如何批量打印出黑白颜色的CAD图纸?
  4. word学习-基础排版(标尺+查看标题+显示标记)
  5. 小区门禁卡可以复制到手机上吗_手机NFC可以复制小区用的门禁卡吗?
  6. 动态链接1 程序员的自我修养第七章笔记
  7. js阻止子元素事件_阻止 JS 的冒泡事件
  8. Linux-更改终端字体大小
  9. c语言强制转换字符类型,C语言数据类型转换实例代码
  10. 软考高级-信息系统管理师之人力资源常见问题(最新版)