数据结构划一下水

Description

N柱砖,希望有连续K柱的高度是一样的. 你可以选择以下两个动作 1:从某柱砖的顶端拿一块砖出来,丢掉不要了. 2:从仓库中拿出一块砖,放到另一柱.仓库无限大. 现在希望用最小次数的动作完成任务.

Input

第一行给出N,K. (1 ≤ k ≤ n ≤ 100000), 下面N行,每行代表这柱砖的高度.0 ≤ hi ≤ 1000000

Output

最小的动作次数


题目大意

有一个非负的数列,可以±1修改高度,求最小代价使得连续k个高度相同

题目分析

对于一个区间的答案,就相当于把所有数都放在数轴上,再求一个数使得它到所有数的总和最小。那么最优就等于是求一个区间的中位数。

于是问题相当于一个支持  求中位数;求比中位数小/大的数个数;求比中位数小/大的数总和  的数据结构。这个问题可以用主席树在$logn$内完成。

注意 printf(calc(),a,b) ,如果在calc()中改变了a,b,输出的a,b将会是改变之前的值。

 #include<bits/stdc++.h>
typedef long long ll;
const int maxn = ;
const int maxNode = ; struct node
{
int val,l,r;
ll sum;
}a[maxNode];
ll ans,lsum,rsum,lcnt,rcnt;
int n,k;
int rt[maxn],w[maxn],cnt[maxn],tot; int read()
{
char ch = getchar();
int num = , fl = ;
for (; !isdigit(ch); ch=getchar())
if (ch=='-') fl = -;
for (; isdigit(ch); ch=getchar())
num = (num<<)+(num<<)+ch-;
return num*fl;
}
void build(int &rt, int l, int r)
{
rt = ++tot;
if (l==r) return;
int mid = (l+r)>>;
build(a[rt].l, l, mid);
build(a[rt].r, mid+, r);
}
void update(int pre, int &rt, int l, int r, int c)
{
rt = ++tot, a[rt] = a[pre], ++a[rt].val, a[rt].sum += cnt[c];
if (l==r) return;
int mid = (l+r)>>;
if (c <= mid) update(a[pre].l, a[rt].l, l, mid, c);
else update(a[pre].r, a[rt].r, mid+, r, c);
}
int query(int pre, int rt, int l, int r, int k)
{
if (l==r) return l;
int val = a[a[rt].l].val-a[a[pre].l].val, mid = (l+r)>>;
if (val >= k){
lcnt -= a[a[rt].r].val-a[a[pre].r].val;
lsum -= a[a[rt].r].sum-a[a[pre].r].sum;
return query(a[pre].l, a[rt].l, l, mid, k);
}
rcnt -= a[a[rt].l].val-a[a[pre].l].val;
rsum -= a[a[rt].l].sum-a[a[pre].l].sum;
return query(a[pre].r, a[rt].r, mid+, r, k-val);
}
int main()
{
n = read(), k = read(), ans = 1ll<<;
for (int i=; i<=n; i++) w[i] = cnt[i] = read();
std::sort(cnt+, cnt+n+);
cnt[] = std::unique(cnt+, cnt+n+)-cnt-;
build(rt[], , cnt[]);
for (int i=; i<=n; i++)
{
w[i] = std::lower_bound(cnt+, cnt+cnt[]+, w[i])-cnt;
update(rt[i-], rt[i], , cnt[], w[i]);
}
for (int r=k; r<=n; r++)
{
int l = r-k;
lcnt = rcnt = a[rt[r]].val-a[rt[l]].val, lsum = rsum = a[rt[r]].sum-a[rt[l]].sum;
int tmp = cnt[query(rt[l], rt[r], , cnt[], (k+)>>)];
ans = std::min(ans, 1ll*tmp*(lcnt-rcnt)-lsum+rsum);
}
printf("%lld\n",ans);
return ;
}

END

【主席树】bzoj1112: [POI2008]砖块Klo的更多相关文章

  1. [BZOJ1112][POI2008]砖块Klo

    [BZOJ1112][POI2008]砖块Klo 试题描述 N柱砖,希望有连续K柱的高度是一样的. 你可以选择以下两个动作 1:从某柱砖的顶端拿一块砖出来,丢掉不要了. 2:从仓库中拿出一块砖,放到另 ...

  2. [Bzoj1112][POI2008]砖块Klo(splay)

    1112: [POI2008]砖块Klo Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 2353  Solved: 831[Submit][Statu ...

  3. [BZOJ1112] [POI2008] 砖块Klo (treap)

    Description N柱砖,希望有连续K柱的高度是一样的. 你可以选择以下两个动作 1:从某柱砖的顶端拿一块砖出来,丢掉不要了. 2:从仓库中拿出一块砖,放到另一柱.仓库无限大. 现在希望用最小次 ...

  4. 【枚举】【权值分块】bzoj1112 [POI2008]砖块Klo

    枚举长度为m的所有段,尝试用中位数更新答案. 所以需要数据结构,支持查询k大,以及大于/小于 k大值 的数的和. 平衡树.权值线段树.权值分块什么的随便呢. #include<cstdio> ...

  5. BZOJ1112[POI2008]砖块Klo——非旋转treap

    题目描述 N柱砖,希望有连续K柱的高度是一样的. 你可以选择以下两个动作 1:从某柱砖的顶端拿一块砖出来,丢掉不要了. 2:从仓库中拿出一块砖,放到另一柱.仓库无限大. 现在希望用最小次数的动作完成任 ...

  6. 【BZOJ1112】[POI2008]砖块Klo Treap

    [BZOJ1112][POI2008]砖块Klo Description N柱砖,希望有连续K柱的高度是一样的. 你可以选择以下两个动作 1:从某柱砖的顶端拿一块砖出来,丢掉不要了. 2:从仓库中拿出 ...

  7. BZOJ 1112: [POI2008]砖块Klo

    1112: [POI2008]砖块Klo Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 1736  Solved: 606[Submit][Statu ...

  8. 1112: [POI2008]砖块Klo

    1112: [POI2008]砖块Klo Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 1245  Solved: 426[Submit][Statu ...

  9. BZOJ 1112 [POI2008]砖块Klo(可持久化线段树)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=1112 [题目大意] 给出一个数列,对于一个操作,你可以对一个数+1,或者一个数-1, ...

随机推荐

  1. 基于IDEA实现SSM整合框架的搭建配置流程

    1.创建数据库表,以员工信息表为例子: DROP TABLE IF EXISTS `em_info`; CREATE TABLE `em_info` ( `em_id` INT(50) NOT NUL ...

  2. webpack4.0介绍与使用(一)

    1:webpack的基本使用: ##在网页中会引用那些静态资源: js, css, images, 字体文件和模板文件(.vue)等 ##网页总引用静态资源多了以后会有那些问题: 网页加载速度慢,因为 ...

  3. JQuery Easyui/TopJUI 创建多级联动下拉框(纯HTML实现!!!)

    JQuery Easyui/TopJUI 创建多级联动下拉框(纯HTML实现!!!) 效果展示: 代码如下: <form data-toggle="topjui-form"& ...

  4. Table 自定义设置边框线

    table上添加:border-collapse: collapse;//设置表格边框分开显示就可以设置tr td的边框线

  5. easyui---datalist相关知识

    datalist 笔记: class:class="easyui-datalist" //对应标准元素:ul 表格线:lines="true" 远程数据绑定: ...

  6. loj6198谢特 后缀数组+并查集+Trie

    先把问题放在后缀数组上考虑 已知两个数组a b,求min(a[i],...,a[j])+(b[i]^b[j])的最大值 套路题 初始每个点都是一个小连通块 把a按从大到小的顺序加入,计算当前加入边作为 ...

  7. Linux上安装Docker,并成功部署NET Core 2.0

    概述 容器,顾名思义是用来存放并容纳东西的器皿: 而容器技术伴着Docker的兴起也渐渐的映入大家的眼帘,它是一个抽象的概念,同时也是默默存在世上多年的技术,不仅能使应用程序间完全的隔离,而且还能在共 ...

  8. 《四 spring源码》手写springioc框架

    手写SpringIOCXML版本 /** * 手写Spring专题 XML方式注入bean * * * */ public class ClassPathXmlApplicationContext { ...

  9. hashMap的具体实现

    HashMap是Java中的一个重要的数据结构! 与HashMap更重要的一个数据结构是HashTable,其中最重要的区别是HashTable传说中是线程安全的(之所以说他是传说是因为我并没有去理解 ...

  10. left join \ right join \ inner join 详解

    left join 和 left outer join 的区别 通俗的讲:   A   left   join   B   的连接的记录数与A表的记录数同   A   right   join   B ...