快排+树状数组+线段树+离散化+扫描线
快排1;
#include<bits/stdc++.h> using namespace std; int a[5] = { 5,1,2,4,3 }; int partition(int begin, int end) { int pivot = begin - 1; for (int i = begin; i <= end - 1; i++) if (a[i] < a[end]) swap(a[i], a[++pivot]); swap(a[++ pivot], a[end]); return pivot; } void quicksort(int begin, int end) { if (begin < end) { int pivot = partition(begin, end); quicksort(begin, pivot - 1); quicksort(pivot + 1, end); } } int main() { quicksort(0, 4); for (int i = 0; i < 5; i++)cout << a[i] << " "; return 0; }
快排2:
#include<bits/stdc++.h> using namespace std; int a[]={0,0,5,1,7,6}; void q(int l,int r){ if(l>=r)return ; int t=a[l+r>>1],i=l-1,j=r+1; while(i<j){ do i++; while(a[i]<t); do j--; while(a[j]>t); if(i<j)swap(a[i],a[j]); } q(l,j); q(j+1,r); } int main(){ q(1,5); for(int i=1;i<=5;i++)cout<<a[i]<<' '; return 0; }
对于十字链表的储存:
#include<bits/stdc++.h> using namespace std; void add(); void creat(crosslist& a); void init(); void print(); struct node { int i, j; int value; node* right, *down; }; struct crosslist { int row, col; int tu; node* rhead, * dhead; }; int m, n; crosslist a; void creat(crosslist& a) { for (int i = 0; i < a.tu; i++) { node* temp; cin >> temp->i >> temp->j >> temp->value; temp->right = temp->down = NULL; if (a.rhead[temp->i].right == NULL) { a.rhead[temp->i].right = temp; } else { node* p = a.rhead[i].right; while (p->right && p->right->j < temp->j) { p = p->right; } temp->right = p->right; p->right = temp; }//行插入成功! if (a.dhead[temp->j].down = NULL) { a.dhead[temp->j].down = temp; } else { node* p = a.dhead[temp->j].down; while (p->down && p->down->i < temp->i) { p = p->down; } temp->down = p->down; p->down = temp; }//列插入成功! } } void init() { a.rhead = a.dhead = NULL; cin >> a.row >> a.col >> a.tu; a.rhead = new node[n]; a.dhead = new node[m]; //初始化行和列的头 for (int i = 0; i < n; i++) { a.rhead[i].down = NULL; } for (int i = 0; i < m; i++) { a.dhead[i].right = NULL; } creat(a); }
树状数组1:
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<bits/stdc++.h> using namespace std; const int N = 2e6; int m,a[N],n,x,y,k,temp; struct node{ int sum,l,r; }t[N]; void build(int i,int l,int r){ if(l==r){ t[i].l=t[i].r=l; t[i].sum=a[l]; return; } t[i].l=l,t[i].r=r; int mid=l+r>>1; build(2*i,l,mid); build(2*i+1,mid+1,r); t[i].sum=t[i*2].sum+t[i*2+1].sum; } void add(int i,int x,int k){//单点修改,x,+k if(t[i].l==t[i].r){ t[i].sum+=k; return ; } int mid=t[i].l+t[i].r>>1; if(x<=mid){ add(i*2,x,k); }else{ add(i*2+1,x,k); } t[i].sum+=k; } int query(int i,int l,int r){//区间查询 if(t[i].l>=l && t[i].r<=r)return t[i].sum; if(t[i].l>r||t[i].r<l)return 0; int s=0; s+=query(i*2,l,r); s+=query(i*2+1,l,r); return s; } int main(){ cin.tie(0); cin.sync_with_stdio(false); cin>>n>>m; for(int i=1;i<=n;i++){ cin>>a[i]; } build(1,1,n); for(int i=1;i<=m;i++){ cin>>temp; if(temp==1){ cin>>x>>k; add(1,x,k); }else{ cin>>x>>y; cout<<query(1,x,y)<<endl; } } return 0; }
树状数组2:
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<bits/stdc++.h> using namespace std; const int N = 2e6; int m,a[N],n,x,y,k,temp,res; struct node{ int sum,l,r; }t[N]; void build(int i,int l,int r){ if(l==r){ t[i].l=t[i].r=l; t[i].sum=a[l]; return; } t[i].l=l,t[i].r=r; int mid=l+r>>1; build(2*i,l,mid); build(2*i+1,mid+1,r); } void add(int i,int x,int y,int k){//区间修改,x,y,+k if(t[i].l>=x&&t[i].r<=y){ t[i].sum+=k; return ; } if(t[i].l>y||t[i].r<x)return; add(i*2,x,y,k); add(i*2+1,x,y,k); } void query(int i,int x){//单点查询 res+=t[i].sum; if(t[i].l==t[i].r)return; int mid=t[i].l+t[i].r>>1; if(x<=mid)query(i<<1,x); else query(i<<1|1,x); } int main(){ cin.tie(0); cin.sync_with_stdio(false); cin>>n>>m; for(int i=1;i<=n;i++){ cin>>a[i]; } build(1,1,n); for(int i=1;i<=m;i++){ cin>>temp; if(temp==1){ cin>>x>>y>>k; add(1,x,y,k); }else{ cin>>x; res=0; query(1,x); cout<<res<<endl; } } return 0; }
树状数组1和树状数组2的区间操作中,对于包含的直接出结果,不包含的直接返回,剩下的就是不全包含的,直接递归就完事了,不用费心想什么边界情况。
这哥俩的细微区别还在于初始化的时候。
线段树模板过不去,不知道为啥。
来点ST模板:
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<bits/stdc++.h> using namespace std; const int N=1e5+5; int a[N][21],l,r,n,m; inline int read() { int x=0,f=1;char ch=getchar(); while (ch<'0'||ch>'9'){if (ch=='-') f=-1;ch=getchar();} while (ch>='0'&&ch<='9'){x=x*10+ch-48;ch=getchar();} return x*f; } int main(){ n=read(),m=read(); for(int i=1;i<=n;i++)a[i][0]=read(); for(int j=1;j<21;j++){ for(int i=1;i+(1<<j-1)<=n;i++){//注意边界! a[i][j]=max(a[i][j-1],a[i+(1<<j-1)][j-1]); } }//nlogn的预处理 while(m--){ l=read(),r=read(); int k=log2(r-l+1); printf("%d\n",max(a[l][k],a[r-(1<<k)+1][k])); } return 0; }
离散化代码:
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
#include<bits/stdc++.h> using namespace std; int main(){ int n,a[100]; cin>>n; for(int i=1;i<=n;i++)cin>>a[i]; sort(a+1,a+1+n); int tot=unique(a+1,a+1+n)-a-1; for(int i=1;i<=tot;i++)cout<<a[i]<<' '; return 0; } //lld只能以十进制输入,lli可以以10、16、8进制输入 //scanf只要%x,%o即可控制进制 //cin需要hex,oct