(待修莫队 没过! 抽空在检查)Dynamic len(set(a[L:R])) UVA - 12345

#include <iostream>
#include <cstdio>
#include <sstream>
#include <cstring>
#include <map>
#include <set>
#include <vector>
#include <stack>
#include <queue>
#include <algorithm>
#include <cmath>
#define MOD 2018
#define LL long long
#define ULL unsigned long long
#define Pair pair<int, int>
#define mem(a, b) memset(a, b, sizeof(a))
#define _  ios_base::sync_with_stdio(0),cin.tie(0)
//freopen("1.txt", "r", stdin);
using namespace std;
const int maxn = 50004, INF = 0x7fffffff;
int n, m, pos[maxn], s[1000005], c[maxn], ans, t[maxn];
int qsz, csz;
struct node
{
    int l, r, t, id, res;
}Node[maxn];

void add(int l, int r, int t, int id)
{
    Node[id].l = l;
    Node[id].r = r;
    Node[id].t = t;
    Node[id].id = id;
}
int l = 1, r = 0, T = 0;
struct change
{
    int pos, Old, New;
}Cha[maxn];

void add_(int pos, int New, int Old, int cnt)
{
    Cha[cnt].pos = pos;
    Cha[cnt].New = New;
    Cha[cnt].Old = Old;
}

bool cmp(node a, node b)
{
    if(pos[a.l] == pos[b.l])
    {
        if(pos[a.r] == pos[b.r])
            return a.t < b.t;
        return pos[a.r] < pos[b.r];
    }
    return pos[a.l] < pos[b.l];
}

bool cmp_id(node a, node b)
{
    return a.id < b.id;
}

void ad(int val)
{
    s[val]++;
    if(s[val] == 1)
        ans++;
}

void de(int val)
{
    s[val]--;
   // cout<< ans <<endl;
    if(s[val] == 0)
        ans--;
}

void go(int idx, int val)
{
    if(l <= idx && idx <= r)
    {
        de(c[idx]);
        ad(val);
    }
    c[idx] = val;
}

int main()
{
    qsz = csz = 0;
    ans = 0;
    scanf("%d%d", &n, &m);
    for(int i=1; i<=n; i++)
    {
        scanf("%d", &c[i]);
        t[i] = c[i];
    }
    int block = pow(n, 2.0/3);
    for(int i=1; i<=n; i++)
        pos[i] = (i-1)/block + 1;
    for(int i=1; i<=m; i++)
    {
        char str[5];
        int x, y;
        scanf("%s%d%d", str, &x, &y);
        if(str[0] == ‘Q‘)
        {
            add(++x, y, csz, ++qsz);
        }
        else
        {
            add_(++x, y, t[x], ++csz);
            t[x] = y;
        }
    }
    sort(Node+1, Node+1+qsz, cmp);
//    for(int i=1; i<=qsz; i++)
//        cout<< Node[i].l << "  " << Node[i].r << endl;
    for(int i=1; i<=qsz; i++)
    {
        for(; T < Node[i].t; T++)
            go(Cha[T+1].pos, Cha[T+1].New);
        for(; T > Node[i].t; T--)
            go(Cha[T].pos, Cha[T].Old);

        for(; r < Node[i].r; r++)
            ad(c[r+1]);
        for(; r > Node[i].r; r--)
            de(c[r]);
        for(; l < Node[i].r; l++)
            de(c[l]);
        for(; l > Node[i].l; l--)
            ad(c[l-1]);
//        for(; T < Node[i].t; T++)
//            go(Cha[T+1].pos, Cha[T+1].New);
//        for(; T > Node[i].t; T--)
//            go(Cha[T].pos, Cha[T].Old);

        Node[i].res = ans;
    }
    sort(Node+1, Node+qsz+1, cmp_id);
    for(int i=1; i<=qsz; i++)
        printf("%d\n",Node[i].res);

    return 0;
}

原文地址:https://www.cnblogs.com/WTSRUVF/p/9348152.html

时间: 2024-11-10 11:41:33

(待修莫队 没过! 抽空在检查)Dynamic len(set(a[L:R])) UVA - 12345的相关文章

CF940F Machine Learning(带修莫队)

首先显然应该把数组离散化,然后发现是个带修莫队裸题,但是求mex比较讨厌,怎么办?其实可以这样求:记录每个数出现的次数,以及出现次数的出现次数.至于求mex,直接暴力扫最小的出现次数的出现次数为0的正整数,就一句话,这样看似会超时,实际上是O(√n)的复杂度.为什么?假设存在出现1,2,...,x的出现次数,则Σi(1<=i<=x)<=n,即x*(x+1)<=2*n,所以x至多是√n级别.很多人再把出现次数分块,根本没必要.然后考虑把数组分块的块大小,每次移动左指针,为O(n*块大

【BZOJ-3052】糖果公园 树上带修莫队算法

3052: [wc2013]糖果公园 Time Limit: 200 Sec  Memory Limit: 512 MBSubmit: 883  Solved: 419[Submit][Status][Discuss] Description Input Output Sample Input Sample Output 84 131 27 84 HINT Source Solution 树上带修莫队 本质还是树上莫队,详情可以转 BZOJ-3757苹果树 但是这里需要修改,就需要一些特殊的地方

【带修莫队】【权值分块】bzoj3196 Tyvj 1730 二逼平衡树

这题用了三种算法写: 分块+二分:O(n*sqrt(n*log(n)) 函数式权值分块:O(n*sqrt(n)) 带修莫队+权值分块:O(n5/3) 结果……复杂度越高的实际上跑得越快……最后这个竟然进第一页了…… #include<cstdio> #include<cstring> #include<cmath> #include<algorithm> using namespace std; int f,C; inline void R(int &

2120: 数颜色(带修莫队)

题目链接:https://www.lydsy.com/JudgeOnline/problem.php?id=2120 2120: 数颜色 Time Limit: 6 Sec  Memory Limit: 259 MBSubmit: 10514  Solved: 4398[Submit][Status][Discuss] Description 墨墨购买了一套N支彩色画笔(其中有些颜色可能相同),摆成一排,你需要回答墨墨的提问.墨墨会像你发布如下指令: 1. Q L R代表询问你从第L支画笔到第R

莫队 + 带修莫队

莫队其实就是一个带优化的暴力,通过将区间询问按一定规则进行排序,从而优化过程,求出答案. 举一例子:(例子不具备权威性,只是让读者了解莫队是干啥的) /* 输入四个区间 1 4 初始条件,L= R = 0, 将R遍历到4 需要走4步 L走一步,共5次 4 8 继承上一次 L 和 R 的值,L从1到4 需要3次,R从4到8,需4次, 总计8次 2 9 同理继承, L回退2次, R前进一次 总计3次 1 2 同理,L回退1次,R回退7次 总计8次 如果直接暴力,计算机将要计算 5+8+3+8=24次

bzoj4129 Haruna’s Breakfast 树上带修莫队+分块

题目传送门 https://lydsy.com/JudgeOnline/problem.php?id=4129 题解 考虑没有修改的序列上的版本应该怎么做: 弱化的题目应该是这样的: 给定一个序列,每次询问区间 \([l, r]\) 中元素的最小没有出现的自然数. 这个弱化的版本可以用离线+线段树二分水掉.但是这个做法显然不太好搬到树上做. 上面的弱化版还有一个莫队做法:可以用莫队维护出来每一个区间的每一个数的出现为次数.把出现过的数通过分块表示出来,于是查询的时候枚举每一个块,寻找第一个不满的

数颜色(带修莫队模板)

数颜色(luogu) Description 题目描述 墨墨购买了一套N支彩色画笔(其中有些颜色可能相同),摆成一排,你需要回答墨墨的提问.墨墨会向你发布如下指令: 1. Q L R代表询问你从第L支画笔到第R支画笔中共有几种不同颜色的画笔. 2. R P Col 把第P支画笔替换为颜色Col. 为了满足墨墨的要求,你知道你需要干什么了吗? 输入格式 第1行两个整数N,M,分别代表初始画笔的数量以及墨墨会做的事情的个数. 第2行N个整数,分别代表初始画笔排中第i支画笔的颜色. 第3行到第2+M行

BZOJ4129(树上带修莫队)

树上莫队的基本思路是把树按dfs序分块,然后先按x所在块从小到大排序,再按y所在块从小到大排序,处理询问即可. 这道题带修改,再加一个时间维即可. 时间复杂度据说是$n^{\frac53}$,不知道是为什么. (块大小改成3也过了什么鬼..) #include <cstdio> #include <algorithm> using namespace std; const int N=50005,M=100005,B=1357,T=223; int n,m,e,x,y,t,tp,o

[带修莫队] Bzoj 2120 数颜色

Description 墨墨购买了一套N支彩色画笔(其中有些颜色可能相同),摆成一排,你需要回答墨墨的提问.墨墨会像你发布如下指令: 1. Q L R代表询问你从第L支画笔到第R支画笔中共有几种不同颜色的画笔. 2. R P Col 把第P支画笔替换为颜色Col.为了满足墨墨的要求,你知道你需要干什么了吗? Input 第1行两个整数N,M,分别代表初始画笔的数量以及墨墨会做的事情的个数.第2行N个整数,分别代表初始画笔排中第i支画笔的颜色.第3行到第2+M行,每行分别代表墨墨会做的一件事情,格