16.7.7 T2:Window
来源:互联网 发布:linux pcb 编辑:程序博客网 时间:2024/06/05 11:42
Description
给你一个长度为N的数组,一个长为K的滑动的窗体从最左移至最右端,你只能见到窗口的K个数,每次窗体向右移动一位,如下表:
你的任务是找出窗口在各位置时的max value,min value.
Input
第1行n,k,第2行为长度为n的数组
Output
2行,第1行每个位置的min value,第2行每个位置的max value
Sample Input
8 3
1 3 -1 -3 5 3 6 7
Sample Output
-1 -3 -3 -3 3 3
3 3 5 5 6 7
Data Constraint
Hint
数据范围:
20%: n<=500; 50%: n<=100000;
100%: n<=1000000
**因为这道题目数据大,而且一次要维护那么多“区间”,于是第一时间想到时间复杂度为O(n log n)的线段树,之前也做过类似的题目,像最大值就是这个的一个缩影:https://jzoj.net/senior/#main/show/1959。
于是,我像做最大值一样维护区间最小值,然后维护最大值,但只能拿90分,让我们来看看原因:n是极端的时候,时间复杂度约为12000000,再加些杂七杂八的都要>25000000,所以呢,两个合并一下,应该可以减少一些复杂度。**
#include<cstdio>#include<iostream>#include<cstring>using namespace std;const int maxn=1000000+500;int n,k;int a[maxn];int treemax[maxn*4];int treemin[maxn*4];int ans1,ans2;int help[maxn][3];inline void buildtree(int x,int left,int right){ if(left==right) treemax[x]=treemin[x]=a[left]; else { int mid=(left+right)/2; buildtree(x*2,left,mid); buildtree(x*2+1,mid+1,right); treemax[x]=max(treemax[x*2],treemax[x*2+1]); treemin[x]=min(treemin[x*2],treemin[x*2+1]); } }/*inline void buildtreemin(int x,int left,int right){ if(left==right) treemin[x]=a[left]; else { int mid=(left+right)/2; buildtreemin(x*2,left,mid); buildtreemin(x*2+1,mid+1,right); treemin[x]=min(treemin[x*2],treemin[x*2+1]); }}*//*void change(int x,int left,int right,int pd,int count){ if(left==right) tree[x]=count; else { int mid=(left+right)/2; if(pd<=mid) change(x*2,left,mid,pd,count); else change(2*x+1,mid+1,right,pd,count); tree[x]=max(tree[x*2],tree[x*2+1]); }}*/inline void treefind(int x,int start,int end,int left,int right){ if(start==left && end==right) {ans1=min(ans1,treemin[x]);ans2=max(ans2,treemax[x]);} else { int mid=(start+end)/2; if(right<=mid) treefind(x*2,start,mid,left,right); else if(left>mid) treefind(x*2+1,mid+1,end,left,right); else { treefind(x*2,start,mid,left,mid); treefind(x*2+1,mid+1,end,mid+1,right); } }}/*inline void treefindmin(int x,int start,int end,int left,int right){ if(start==left && end==right) {ans=min(ans,treemin[x]); else { int mid=(start+end)/2; if(right<=mid) treefindmin(x*2,start,mid,left,right); else if(left>mid) treefindmin(x*2+1,mid+1,end,left,right); else { treefindmin(x*2,start,mid,left,mid); treefindmin(x*2+1,mid+1,end,mid+1,right); } }}*//*inline void treefind(int x,int start,int end,int left,int right){ if(start==left && end==right) { ansmax[top]=max(ansmax[top],treemax[x]); ansmin[top]=min(ansmin[top],treemin[x]); } else { int mid=(start+end)/2; if(right<=mid) treefind(x*2,start,mid,left,right); else if(left>mid) treefind(x*2+1,mid+1,end,left,right); else { treefind(x*2,start,mid,left,mid); treefind(x*2+1,mid+1,end,mid+1,right); } }}*/int main(){ freopen("2.in","r",stdin); scanf("%d %d",&n,&k); for(int i=1;i<=n;i++) scanf("%d",&a[i]); buildtree(1,1,n); int x,y; for(int i=1,j=k;i<=n-k+1,j<=n;i++,j++) { ans1=0x7fffffff; ans2=0; treefind(1,1,n,i,j); help[i][1]=ans1; help[i][2]=ans2; } for(int i=1;i<=n-k+1;i++) { if(i!=n-k+1) printf("%d ",help[i][1]); else printf("%d\n",help[i][1]); } for(int i=1;i<=n-k+1;i++) { if(i!=n-k+1) printf("%d ",help[i][2]); else printf("%d\n",help[i][2]); } return 0;}
0 1
- 16.7.7 T2:Window
- t2
- t2
- t2
- T2
- t2
- T2
- 【2014-7】day3 T2 谈笑风生
- CH Round#48 T2 4和7
- 【DP】17.2.7 T2 隔离村庄 题解
- T2-J
- T2定时器
- 10.18 T2
- NOIp2013PJ T2
- NOIp2004PJ T2
- 【11.14】T2
- T2截屏
- HYSBZ4034-T2
- 在VXVM环境下配置raid01和raid10卷,以及2者间的转换方法
- 内存分配:堆、栈、全局变量/静态变量、代码区
- linux下socket编程学习01
- 【Linux】 进程通信--消息队列
- java基础学习总结——网络编程
- 16.7.7 T2:Window
- 06_ConstructBinaryTree重建二叉树
- DataGridView网格颜色
- C语言创建数组的几个常用方法
- 数组类的使用2(含有类数组的例子)
- java基础学习总结——GUI编程(一)
- SQL Server 数据恢复
- 无锁队列原理和实现
- inspector 绘制总结