• BZOJ 1483: [HNOI2009]梦幻布丁 [链表启发式合并]


    1483: [HNOI2009]梦幻布丁

    题意:一个带颜色序列,一种颜色合并到另一种,询问有多少颜色段


    一种颜色开一个链表,每次遍历小的合并到大的里,顺带维护答案
    等等,合并方向有规定?
    令col[x]代表给颜色x分配的编号,直接交换编号


    WA了三次我还有救吗

    #include <iostream>
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    typedef long long ll;
    #define lc t[x].ch[0]
    #define rc t[x].ch[1]
    #define pa t[x].fa
    const int N=1e5+5, M=1e6+5;
    inline int read(){
        char c=getchar();int x=0,f=1;
        while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
        while(c>='0'&&c<='9'){x=x*10+c-'0';c=getchar();}
        return x*f;
    }
    
    int n, Q, a[N], op, ans, x, y;
    struct meow{int v, ne;}e[M];
    int cnt, h[M], size[M], col[M];
    inline void ins(int u, int v) {
    	e[++cnt]=(meow){v, h[u]}; h[u]=cnt; size[u]++;
    }
    void Merge(int x, int y) { //printf("Merge %d %d
    ",x,y);
    	if(x==y) return;
    	if(size[col[x]]>size[col[y]]) swap(col[x], col[y]);
    	x=col[x], y=col[y]; //printf("col %d %d
    ",x,y);
    	for(int i=h[x];i;i=e[i].ne) {
    		int v=e[i].v; //printf("vvv %d
    ",v);
    		ans-= (a[v-1]==y) + (a[v+1]==y);
    		ins(y, v);
    	}
    	for(int i=h[x];i;i=e[i].ne) a[e[i].v]=y;
    	h[x]=size[x]=0;
    }
    int main() {
    	freopen("in","r",stdin);
    	n=read(); Q=read();  ans=n;
    	for(int i=1; i<=n; i++) a[i]=read(), ins(a[i], i), ans-= a[i]==a[i-1], col[a[i]]=a[i];
    	for(int i=1; i<=Q; i++) {
    		op=read();
    		if(op==1) x=read(), y=read(), Merge(x, y);
    		else printf("%d
    ",ans);
    	}
    }
    
    
  • 相关阅读:
    linux之iptable案例
    nginx常用命令参数
    laravel中的多对多关系详解
    MySql计算时间差函数
    总结下Mysql分表分库的策略及应用
    swoole扩展实现真正的数据库连接池
    linux常用命令整理
    innodb mvcc实现机制
    mysqlslap 压力测试使用总结
    mysql索引总结
  • 原文地址:https://www.cnblogs.com/candy99/p/6621422.html
Copyright © 2020-2023  润新知