题意

让你构造一个长度为n的序列,记为p1……pn,(这个序列是1~n的全排列的一种)

给你n个数,记为s1……sn,si的值为p1……pi-1中小于pi的数的和。

思路

显然,应该倒着来,也就是从p开始构造,这样的话,当要填p的时候,p1到pi-1就是所有的还未填的数,那么我们只需要去找哪个前缀和符合就可以了。

比如:现在还没填进去的数是 1,2,3,4,5

而我现在的si 是6,那么,对应的pi 就是4,因为这样无论1,2,3,5怎么排,都符合si 为6

(才学疏浅,不怎么会讲)

那么,选完要删除,所以要修改前缀和,考虑用树状数组,查找哪个符合,自然是二分。

代码

#include <stdio.h>
#include <queue>
#include <string>
#include <string.h>
#include <algorithm>
#include <math.h>
#include <set>
using namespace std;
typedef long long int ll;
const int maxn = 2e5 + ;
const int inf = ;
const ll mod = ;
const ll seed = ;
ll s[maxn],c[maxn],ans[maxn],n;
int lowbit(int x)
{
return x & (-x);
}
void insert(ll x,int i)
{
while(i <= n){
c[i] += x;
i += lowbit(i);
}
}
ll getsum(int i)
{
ll sum = ;
while(i > ){
sum += c[i];
i -= lowbit(i);
}
return sum;
}
int vis[maxn];
int query(ll x)
{
int l,r,mid;
ll res;
l = ;r = n;
while(l <= r){
mid = (l + r) >> ;
res = getsum(mid);
if(res == x){
if(vis[mid + ])
l = mid + ;
else
return mid;
}
else if(res < x){
l = mid + ;
}
else{
r = mid - ;
}
}
}
int main()
{
while(scanf("%d",&n) != EOF){
memset(vis,,sizeof(vis));
memset(c,,sizeof(c));
for(int i = ;i <= n;i++){
scanf("%lld",&s[i]);
insert(i,i);
} for(int i = n;i >= ;i--){
ans[i] = query(s[i]) + ;
vis[ans[i]] = ;
insert(-ans[i],ans[i]);
}
for(int i = ;i <= n;i++)
printf("%d ",ans[i]);
puts("");
}
return ;
}

cf1208 D Restore Permutation (二分+树状数组)的更多相关文章

  1. Manthan, Codefest 19 (open for everyone, rated, Div. 1 + Div. 2)-D. Restore Permutation-构造+树状数组

    Manthan, Codefest 19 (open for everyone, rated, Div. 1 + Div. 2)-D. Restore Permutation-构造+树状数组 [Pro ...

  2. 【BZOJ-2527】Meteors 整体二分 + 树状数组

    2527: [Poi2011]Meteors Time Limit: 60 Sec  Memory Limit: 128 MBSubmit: 831  Solved: 306[Submit][Stat ...

  3. 【BZOJ3110】【整体二分+树状数组区间修改/线段树】K大数查询

    Description 有N个位置,M个操作.操作有两种,每次操作如果是1 a b c的形式表示在第a个位置到第b个位置,每个位置加入一个数c 如果是2 a b c形式,表示询问从第a个位置到第b个位 ...

  4. BZOJ_3110_[Zjoi2013]K大数查询_整体二分+树状数组

    BZOJ_3110_[Zjoi2013]K大数查询_整体二分+树状数组 Description 有N个位置,M个操作.操作有两种,每次操作如果是1 a b c的形式表示在第a个位置到第b个位置,每个位 ...

  5. bzoj千题计划316:bzoj3173: [Tjoi2013]最长上升子序列(二分+树状数组)

    https://www.lydsy.com/JudgeOnline/problem.php?id=3173 插入的数是以递增的顺序插入的 这说明如果倒过来考虑,那么从最后一个插入的开始删除,不会对以某 ...

  6. 【bzoj3110】[Zjoi2013]K大数查询 整体二分+树状数组区间修改

    题目描述 有N个位置,M个操作.操作有两种,每次操作如果是1 a b c的形式表示在第a个位置到第b个位置,每个位置加入一个数c.如果是2 a b c形式,表示询问从第a个位置到第b个位置,第C大的数 ...

  7. zoj-3963 Heap Partition(贪心+二分+树状数组)

    题目链接: Heap Partition Time Limit: 2 Seconds      Memory Limit: 65536 KB      Special Judge A sequence ...

  8. 【bzoj4009】[HNOI2015]接水果 DFS序+树上倍增+整体二分+树状数组

    题目描述 给出一棵n个点的树,给定m条路径,每条路径有一个权值.q次询问求一个路径包含的所有给定路径中权值第k小的. 输入 第一行三个数 n和P 和Q,表示树的大小和盘子的个数和水果的个数. 接下来n ...

  9. UVA 11525 Permutation (树状数组+YY)

    题意:给你k个数Si,然后给你一个等式   H= ∑  Si ∗ (K − i)!  (i=(1->k)且0 ≤ Si ≤ K − i). 叫你求出第H个全排列 其实这是一个康托展开:X=a[n ...

  10. 【bzoj2527】[Poi2011]Meteors 整体二分+树状数组

    题目描述 有N个成员国.现在它发现了一颗新的星球,这颗星球的轨道被分为M份(第M份和第1份相邻),第i份上有第Ai个国家的太空站. 这个星球经常会下陨石雨.BIU已经预测了接下来K场陨石雨的情况.BI ...

随机推荐

  1. zabbix_get工具基础使用

    zabbix_get工具基础使用 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.zabbix_get工具概述 我们在使用zabbix server监控zabbix agent端 ...

  2. Program-Language

    1. 主流编程语言 2. 编程语言分类     2.1 编译or解释     2.2 按照客观系统的描述可分为两类     2.3 按照编程范型可分为 3. 语言范式 Paradigm 4. 计算机语 ...

  3. JS浮点数的研究

    为什么0.1 + 0.2 得到的是 0.30000000000000004 console.log( 0.1 + 0.2 == 0.3);//false 在js中所有的整数和小数都是以Number形式 ...

  4. 三十二、CI框架之配置域名和设置默认登陆网站

    一.打开routes.php文件,将$route['default_controller'] = 'login'; 修改成我们需要的内容. 二.修改config.php中的base_url数据 三.L ...

  5. JS:利用for循环进行数组去重

    <script> var a = [1, 3, 2, 4, 5, 3, 2, 1, 4, 6, 7, 7, 6, 6]; //示例数组    var b = []; for(var i = ...

  6. 六、Vue-Router:基础路由处理、路由提取成单独文件、路由嵌套、路由传参数、路由高亮、html5的history使用

    一.vue-router的安装 官网文档 [官网]:https://cn.vuejs.org/v2/guide/routing.html [router文档]:https://router.vuejs ...

  7. Linux每日练习-批量删除用户,非脚本运行方式 20200225

  8. redis的配置文件介绍

    目录 1.开头说明 2.INCLUDES 3.MODULES 4.NETWORK 5.GENERAL 6.SNAPSHOTTING 7.REPLICATION 8.SECURITY 9.CLIENTS ...

  9. windows查看所有进程:netstat -ano

    windows查看所有进程:netstat -ano ------------------------------------------------------------------------- ...

  10. C++ for无限循环~

    无限循环 如果条件永远不为假,则循环将变成无限循环.for 循环在传统意义上可用于实现无限循环.由于构成循环的三个表达式中任何一个都不是必需的,您可以将某些条件表达式留空来构成一个无限循环. #inc ...