NYOJ511 移动小球(链表基础题)(链表法+非链表法)
2012-03-29 09:15
309 查看
-传送门-
这道题很容易想到要构建一个循环链表来确定每个球的相对位置,就是操作比较繁琐,考虑情况较多。
首先要创建节点Node,每个节点都有一个初始顺序order,指向左边的Node*指针left,和指向右边的Node*指针right。
然后给每个小球附上顺序,并建立和左右的联系。
1.将x左边节点的right指针指向x的右边节点
2.将x右边节点的left指针指向x的左边节点
3.将x的right指向y节点
4.将x的left指向y左边的节点
5.将y左边节点的right指向x节点
6.将y的left指向x节点
实现代码:
由于交换位置仅改变节点的左右指针,并没有改变数组的下标(下标其实与order相同),所以查找球号时直接用下标索引。
同理可知操作B。
完整代码如下:
其实此题还可以不用链表,对比了一下,时间相差不大,相比而言非链表法更不容易出错。
思路基本一样,直接给出代码:
这道题很容易想到要构建一个循环链表来确定每个球的相对位置,就是操作比较繁琐,考虑情况较多。
首先要创建节点Node,每个节点都有一个初始顺序order,指向左边的Node*指针left,和指向右边的Node*指针right。
struct Node { int order; Node *left,*right; }node ;
然后给每个小球附上顺序,并建立和左右的联系。
void build(int n) { int i,order=1; for(i=1;i<n;i++) { node[i].order=i; node[i].right=&node[i+1]; node[i+1].left=&node[i]; } node[1].left=&node ; node .right=&node[1]; node .order=n; }然后就是A、B操作,下边叙述一下A操作(将x放在y左边)的实现方法:
1.将x左边节点的right指针指向x的右边节点
2.将x右边节点的left指针指向x的左边节点
3.将x的right指向y节点
4.将x的left指向y左边的节点
5.将y左边节点的right指向x节点
6.将y的left指向x节点
实现代码:
void A(int x,int y) { Node *p=&node[x],*q=&node[y]; p->left->right=p->right; p->right->left=p->left; p->left=q->left; p->right=q; q->left->right=p; q->left=p; }
由于交换位置仅改变节点的左右指针,并没有改变数组的下标(下标其实与order相同),所以查找球号时直接用下标索引。
同理可知操作B。
完整代码如下:
#include<stdio.h>
const int N=10005;
struct Node { int order; Node *left,*right; }node ;
void build(int n) { int i,order=1; for(i=1;i<n;i++) { node[i].order=i; node[i].right=&node[i+1]; node[i+1].left=&node[i]; } node[1].left=&node ; node .right=&node[1]; node .order=n; }
void A(int x,int y) { Node *p=&node[x],*q=&node[y]; p->left->right=p->right; p->right->left=p->left; p->left=q->left; p->right=q; q->left->right=p; q->left=p; }
void B(int x,int y)
{
Node *p=&node[x],*q=&node[y];
p->left->right=p->right;
p->right->left=p->left;
p->right=q->right;
q->right->left=p;
p->left=q;
q->right=p;
}
int main()
{
int ncase,n,m,i;
char cmd;
int x,y;
scanf("%d",&ncase);
while(ncase--)
{
scanf("%d%d",&n,&m);
build(n);
while(m--)
{
scanf("%*c%c%d%d",&cmd,&x,&y);
switch(cmd)
{
case 'A':
A(x,y);break;
case 'B':
B(x,y);break;
case 'Q':
printf("%d\n",x?node[y].right->order:node[y].left->order);break;
}
}
}
return 0;
}
其实此题还可以不用链表,对比了一下,时间相差不大,相比而言非链表法更不容易出错。
思路基本一样,直接给出代码:
#include<cstdio> const int N=10005; struct xyz { int prv,nxt; }a ; void build(int n) { int i; for(i=1;i<=n;i++) { a[i].prv=i-1; a[i].nxt=i+1; } a[1].prv=n; a .nxt=1; } void A(int x,int y) { a[a[x].prv].nxt=a[x].nxt; a[a[x].nxt].prv=a[x].prv; a[x].nxt=y; a[x].prv=a[y].prv; a[a[y].prv].nxt=x; a[y].prv=x; } void B(int x,int y) { a[a[x].prv].nxt=a[x].nxt; a[a[x].nxt].prv=a[x].prv; a[x].nxt=a[y].nxt; a[x].prv=y; a[a[y].nxt].prv=x; a[y].nxt=x; } int main() { int ncase,n,m,i; char cmd; int x,y; scanf("%d",&ncase); while(ncase--) { scanf("%d%d",&n,&m); build(n); while(m--) { scanf("%*c%c%d%d",&cmd,&x,&y); switch(cmd) { case 'A': A(x,y);break; case 'B': B(x,y);break; case 'Q': printf("%d\n",x?a[y].nxt:a[y].prv);break; } } } return 0; }
相关文章推荐
- NYOJ 511 - 移动小球 链表版
- NYOJ 511 移动小球
- NYOJ 题目511 移动小球(双向循环链表)
- NYOJ-511 移动小球【模拟】
- NYOJ 511 移动小球
- [转]NYOJ-511-移动小球
- [转]NYOJ-511-移动小球
- NYOJ-511-移动小球
- NYOJ-移动小球
- 链表水题一道sicily 1934.移动小球 -- 线性结构,链表,水题
- 使用链表实现小球移动
- 算法竞赛入门经典:第六章 数据结构基础 6.3移动小球
- 数组+链表 小球移动过程
- 双向链表nyoj511
- 移动小球链表实现
- 6-2-2 移动的小球(数组模拟链表实现)
- Android从基础做起——自定义View(随手移动的小球)
- nyoj 551 移动小球
- NYOJ 551 移动小球
- 数据结构基础--单链表