紫书第六章-----数据结构基础(数组模拟链表)
来源:互联网 发布:python ftp 传输模式 编辑:程序博客网 时间:2024/05/11 12:49
数组模拟单链表
例题6-4 Broken Keyboard (a.k.a. Beiju Text) UVA - 11988
这道题目可以直接用STL中list双向链表来做,思路和代码都很简单易想。也可以用数组模拟链表(不易懂)。
之所以不用vector是因为插入删除比较慢慢慢
AC代码(一):
STL的list版本
#include<iostream>#include<list>#include<string>using namespace std;int main(){ string s; while(cin>>s){ list<char>l; list<char>::iterator it=l.begin(); for(int i=0;i<s.length();i++){ if(s[i]=='[') it=l.begin(); else if(s[i]==']') it=l.end(); else{ it=l.insert(it,s[i]); it++; } } for(it=l.begin();it!=l.end();it++) cout<<*it; cout<<endl; } return 0;}
AC代码(二):
数组模拟链表版本
//数组模拟链表#include<stdio.h>#include<string.h>const int maxn=100000+5;int next[maxn];//next[i]表示链表中第i个结点下一个结点的编号char s[maxn];int cur;//当前光标所在位置,即指向当前结点的右侧int last;//当前最后一个结点的编号int main(){ //s[0]设置为类似链表的头结点,元素从下标1开始编号 while(scanf("%s",s+1)!=EOF){ int len=strlen(s+1); cur=last=0; next[0]=-1;//这里-1仅仅是一个标记,表示起初链表的头结点指向的数值 //类似于指针链表初始化时候linklist->next=NULL for(int i=1;i<=len;i++){ if(s[i]=='[') cur=0;//光标定位到开始,指向第0个元素(假想的头结点)的右侧 else if(s[i]==']') cur=last;//光标定位到最后一个元素,指向最后一个元素的右侧 else{ //插入新节点i,类似于链表中创建一个节点i,让他的next指向当前链表头(cur)的next //再让当前链表头的next指向节点i //和普通链表不同的是这里的链表头cur会变,但是next[0]永远是第一个字符哦 next[i]=next[cur]; next[cur]=i; if(cur==last) last=i;//如果现在的cur=last,插入新节点后,更新last,手写易明白 //由于cur可能会回到头变成0,所以这个操作技巧很好 cur=i;//插入一个新节点后,cur自然后移,指向当前节点的右侧 } } //上述过程完成了建立一个链表的过程,next[0]的值就是第一个字符的下标,next[1]就是第2个节点 //的下标,以此类推,最后一个节点的next必然是-1,想想链表建立过程,依次往后指,这一点应该很明白 for(int i=next[0];i!=-1;i=next[i]) printf("%c",s[i]); printf("\n"); } return 0;}
C语言代码(超时为何?):
#include<stdio.h>#include<string.h>const int maxn=100000+5;char s[maxn];typedef struct LINK{ LINK *next; LINK *rear; LINK *cur; char c;}node,*linklist;void linklist_init(linklist &lis){ lis=new node; lis->rear=lis; lis->next=NULL; lis->cur=lis;}void linklist_insert(linklist &lis,char e){ node *p=new node; p->next=lis->cur->next; p->c=e; lis->cur->next=p; if(lis->cur==lis->rear) lis->rear=p; lis->cur=p;}int main(){ while(scanf("%s",s)!=EOF){ linklist lis; linklist_init(lis); for(int i=0;i<strlen(s);i++){ if(s[i]=='[') lis->cur=lis; else if(s[i]==']'){lis->cur=lis->rear;} else{ linklist_insert(lis,s[i]); } } node *tmp=lis; while(tmp->next){ printf("%c",tmp->next->c); tmp=tmp->next; } printf("\n"); } return 0;}
数组模拟双向链表
例题6-5 Boxes in a Line UVA - 12657
直接给出参考刘汝佳《算法竞赛入门经典》(第2版)代码参考:
#include<cstdio>const int maxn=100000+5;int n,m;int left[maxn],right[maxn];int kase=0;void link(int l,int r){ right[l]=r; left[r]=l;}int main(){ while(scanf("%d%d",&n,&m)!=EOF){ for(int i=1;i<=n;i++){ left[i]=i-1; right[i]=(i+1)%(n+1); } left[0]=n;right[0]=1; int op,x,y; bool inv=0; while(m--){ scanf("%d",&op); if(op==4) inv=!inv; else{ scanf("%d%d",&x,&y); if(op==3 && right[y]==x){int t=x;x=y;y=t;}//x,y相邻的情形统一变为y在x右侧 //下面这个复合语句坑我了,下面这么写是对的,下面的复合语句全部用if,if是错的 { if(op==2 && inv) op=1;//逆转后,右边变左边,左边变右边 else if(op==1 && inv) op=2; } if(op==1 && x==left[y]) continue; if(op==2 && x==right[y]) continue; int lx=left[x],rx=right[x],ly=left[y],ry=right[y];//这样已经保存了x,y的左右值哦,这样很方便后续操作 if(op==1){ link(lx,rx);link(ly,x);link(x,y); } else if(op==2){ link(lx,rx);link(y,x);link(x,ry); } else if(op==3){ //分为两种情形,x,y相邻与否 if(right[x]==y){ link(lx,y);link(y,x);link(x,ry); } else{ link(lx,y);link(y,rx); link(ly,x);link(x,ry); } } } } int j=0; long long int ans=0; for(int i=1;i<=n;i++){ j=right[j]; if(i%2==1) ans+=j; } if(inv && n%2==0) ans=(long long)n/2*(n+1)-ans; printf("Case %d: %lld\n",++kase,ans); } return 0;}
阅读全文
0 0
- 紫书第六章-----数据结构基础(数组模拟链表)
- 紫书学习之第六章数据结构基础
- 第六章数据结构基础之树部分
- 第六章数据结构基础之图部分
- 第六章:数据结构基础。第一部分
- 第六章:数据结构基础。第二部分
- 第六章:数据结构基础。第三部分
- 第六章:数据结构基础。第四部分
- 基础数据结构之数组与链表(一)
- 基础数据结构之数组和链表(三)
- 基础数据结构之数组与链表(二)
- 基础数据结构之数组与链表(四)
- 基础数据结构之数组与链表(五)
- 数据结构基础:数组和链表
- 第六章 数组(慕课)
- 算法竞赛入门经典(第二版)-刘汝佳-第六章 数据结构基础 例题(17/22)
- 算法竞赛入门经典(第二版)-刘汝佳-第六章 数据结构基础 习题(12/14)
- 算法竞赛入门经典 第六章 数据结构基础
- setStrokeWidth() 方法思考
- final内联函数
- 对<源码级调试WDF框架>一文进行补充
- android精选源码,知乎阅读瀑布流loading弹窗扫描二维码简洁的MVP
- Linux 环境下的抓包工具
- 紫书第六章-----数据结构基础(数组模拟链表)
- 聚类
- OpenGL glm库的投影矩阵公式 glm::perspective
- Class<?> 方法和构造
- Fragment切换(show() and hide())
- qrcode(二)
- thread_info
- Floyd算法(任意两点间的最短路径)
- uboot移植(一)