CSDN 报数游戏-双向循环链表实现
2014-01-06 17:44
295 查看
通过这道题,对于链表的运用感觉灵活了许多……
有n个人编号1-n,按照顺时针方向围成一个圆圈。它们预先定义好两个整数x,y。先从1号顺时针方向开始报数,报到x的人出圈,再从x的逆时针方向的后一个人从1开始报数,报到y的人出圈,再从这个人的顺时针方向后一个人开始从1报数,报到x的人出圈,如此反复,直到最后剩下一个人为止,问最后剩下的那个人是几号?
比如n = 10, x = 3, y = 2,报数的过程如下
报数人 1, 2, 3 3出圈
报数人 2,1 1出圈
接着2,4 ,5 5出圈
接着4,2 2出圈
接着4,6,7 7出圈
接着6,4 4出圈
接着6,8,9 9出圈
接着8,6 6出圈
接着8,10,8 8出圈
剩余 10号。
输入n,x,y输出剩余的编号。
数据范围 1 < n <= 1000000, 1<=x,y<=1000000000。
#include<iostream>
using namespace std ;
struct Node {
int data ;
Node *prier ;
Node *next ;
};
typedef Node *LinkList ;
void Create( LinkList &L , int n ) { //创建双向循环链表
LinkList s , h , p;
L = NULL ;
s = new Node ;
h = s ;
for( int i = n ; i > 0 ; i-- ) {
s->prier = L ;
s->data = i ;
p = new Node ;
s->next = p ;
L = s ;
s = p ; // 此处不能delete p
}
L->next = h ;
h->prier = L ;
}
int Delete( LinkList &L , int x , int y ) { //递归删除第x个、第y个结点
for(int i = 2 ; i <= x ; i++ )
L = L->prier ;
L->prier->next = L->next ;
L->next->prier = L->prier ;
L = L->next ;
if(L->next == L->prier)
return L->next->data ;
for(int j = 2 ; j <= y ; j++ )
L = L->next ;
L->prier->next = L->next ;
L->next->prier = L->prier ;
L = L->prier ;
if(L->next == L->prier)
return L->next->data ;
else
return Delete( L , x , y ) ;
}
int main() {
int n , x , y ;
cin>>n>>x>>y ;
LinkList L ;
Create( L , n ) ;
cout<<Delete( L , x , y )<<endl;
return 0 ;
}
有n个人编号1-n,按照顺时针方向围成一个圆圈。它们预先定义好两个整数x,y。先从1号顺时针方向开始报数,报到x的人出圈,再从x的逆时针方向的后一个人从1开始报数,报到y的人出圈,再从这个人的顺时针方向后一个人开始从1报数,报到x的人出圈,如此反复,直到最后剩下一个人为止,问最后剩下的那个人是几号?
比如n = 10, x = 3, y = 2,报数的过程如下
报数人 1, 2, 3 3出圈
报数人 2,1 1出圈
接着2,4 ,5 5出圈
接着4,2 2出圈
接着4,6,7 7出圈
接着6,4 4出圈
接着6,8,9 9出圈
接着8,6 6出圈
接着8,10,8 8出圈
剩余 10号。
输入n,x,y输出剩余的编号。
数据范围 1 < n <= 1000000, 1<=x,y<=1000000000。
#include<iostream>
using namespace std ;
struct Node {
int data ;
Node *prier ;
Node *next ;
};
typedef Node *LinkList ;
void Create( LinkList &L , int n ) { //创建双向循环链表
LinkList s , h , p;
L = NULL ;
s = new Node ;
h = s ;
for( int i = n ; i > 0 ; i-- ) {
s->prier = L ;
s->data = i ;
p = new Node ;
s->next = p ;
L = s ;
s = p ; // 此处不能delete p
}
L->next = h ;
h->prier = L ;
}
int Delete( LinkList &L , int x , int y ) { //递归删除第x个、第y个结点
for(int i = 2 ; i <= x ; i++ )
L = L->prier ;
L->prier->next = L->next ;
L->next->prier = L->prier ;
L = L->next ;
if(L->next == L->prier)
return L->next->data ;
for(int j = 2 ; j <= y ; j++ )
L = L->next ;
L->prier->next = L->next ;
L->next->prier = L->prier ;
L = L->prier ;
if(L->next == L->prier)
return L->next->data ;
else
return Delete( L , x , y ) ;
}
int main() {
int n , x , y ;
cin>>n>>x>>y ;
LinkList L ;
Create( L , n ) ;
cout<<Delete( L , x , y )<<endl;
return 0 ;
}
相关文章推荐
- 关于android ndk出现ReferenceTable overflow (max=1024)的解决方法
- XACT Q&A (转)
- 【转】linux最新分区方案
- 数据挖掘方法论流程图
- 数据库连接字符串大全
- webservice之获取ip归属地
- debug 64bit dump of a 32bit process in windows 7 64bit
- pipe row 的用法,Oracle split 函数写法
- java 用数据组身oracle中插入数据问题
- 我的个人博客
- 多CPU下基于e1000e驱动的数据包以及网卡中断流程分析.doc
- 位图按钮类,实现了按下、放开和鼠标在按钮上的图片更换。
- linux关机
- 陌陌该怎样卸下约炮神器的“美誉”?
- ubuntu之rsync服务
- Web应用程序与桌面应用程序的区别
- Opennebula4.2管理端和节点SSH模式的安装配置
- TThreadedServer vs. TNonblockingServer
- 小记 有些手机裁剪图片问题
- 数字音乐维权联盟首次出招 QQ音乐起诉酷我索赔千万