A. C语言链表求约瑟夫数学问题
voiddel(node*head,intm)
{
inti;
node*p1,*p2;
p1=head;
while((p1->next)!=p1)//仅剩一个结点时停止循环
{
for(i=1;i<m;i++)//报到m退出,所以从1开始
{//----------这里是不是少了括号?
p2=p1;p1=p1->next;
}//----------
p2->next=p1->next;
p1=p1->next;
}
printf("%d",p1->data);
}
B. C语言 利用链表解决约瑟夫问题
改后的这个看看可不可以
voidprintlist(structman*head,intt)/*这是第三十行*/
{
structman*p=head;
inti,k=1;
for(i=0;i<t;)
{
if(p==NULL)
p=head;
if(p->quan==0)
p=p->next;
elseif(k==3)
{
p->quan;
k=0;
i++;
}
elseif(k<3)
{
p=p->next;
k++;
}
p=head;
}
while(p!=NULL)
{
printf("%d%d ",p->num,p->quan);
p=p->next;
}
}
C. 求解约瑟夫环问题 C语言
链表方法
这个就是约瑟夫环问题的实际场景,有一种是要通过输入n,m,k三个正整数,来求出列的序列。这个问题采用的是典型的循环链表的数据结构,就是将一个链表的尾元素指针指向队首元素。
p->link=head
解决问题的核心步骤:
1.建立一个具有n个链结点,无头结点的循环链表
2.确定第1个报数人的位置
3.不断地从链表中删除链结点,直到链表为空
void
JOSEPHUS(int
n,int
k,int
m)
//n为总人数,k为第一个开始报数的人,m为出列者喊到的数
{
/*
p为当前结点
r为辅助结点,指向p的前驱结点
list为头节点*/
LinkList
p,r,list;
/*建立循环链表*/
for(int
i=0,i<n,i++)
{
p=(LinkList)malloc(sizeof(LNode));
p->data=i;
if(list==NULL)
list=p;
else
r->link=p;
r=p;
}
p>link=list;
/*使链表循环起来*/
p=list;
/*使p指向头节点*/
/*把当前指针移动到第一个报数的人*/
for(i=0;i<k;i++)
{
r=p;
p=p->link;
}
/*循环地删除队列结点*/
while(p->link!=p)
{
for(i=0;i<m-1;i++)
{
r=p;
p=p->link;
}
r->link=p->link;
printf("被删除的元素:%4d
",p->data);
free(p);
p=r->link;
}
printf("\n最后被删除的元素是:%4d",P->data);
}
D. C语言约瑟夫问题
约瑟夫问题:
#include<iostream.h>
struct
node
{
int
data;
node
*pnext;
};
void
main()
{
int
n,k,m,i;
node
*p,*q,*head;
cout<<"输入n的值:";
cin>>n;
cout<<"输入起始报数人号码k的值:";
cin>>k;
cout<<"输入
数到m出列的m的值:";
cin>>m;
head=(node*)new
node;
//确定头结点
p=head;
for(i=1;i<=n-1;i++)
//赋初值
{
p->data=i;
p->pnext=(node*)new
node;
//为下一个新建内存
p=p->pnext;
}
p->data=n;
//最后一个单独处理
p->pnext=head;
//指向头,形成循环链表
p=head;
while(p->data!=(p->pnext)->data)
//p->data==(p->pnext)->data表示只剩下一个结点的
{
while(p->data
!=k)
//寻找编号为k的结点
p=p->pnext;
if(m==1)
{
for(i=1;i<=n;i++)
{
cout<<p->data<<'\\t'
;
p=p->pnext
;
}
cout<<'\
';
return;
}
else
for(i=1;i<m-1;i++)
//开始报数
{p=p->pnext;}
//找到报m-1的结点
q=p->pnext;
//q为报m的结点
cout<<q->data<<"\\t";
//输出报m的结点的值
k=(q->pnext)->data;
//k为下一个报数的起点
p->pnext=q->pnext;
//删除报m的结点
}
cout<<p->data<<'\
';
//输出最后一个结点的值
}
E. C语言编程问题:约瑟夫问题求解
用一个循环链表就可以完成了!
#include<stdio.h>
struct node{
int data;
struct node *next;
}node,*list,*p,*r;
void JOSEPHU(int n,int k,int m)
{
int i,j;
list=NULL;
for(i=1;i<=n;i++)
{
p=(struct node*)malloc(sizeof(node));
p->data=i;
if(list==NULL)
list=p;
else
r->next=p;
r=p;
}
p->next=list; /*建立一个循环链表*/
p=list;
for(i=1;i<=n+1;i++)
{
printf("%d ",p->data);
p=p->next;
}
printf("\n"); /*打印链表,并检查循环链表是不输入正确*/
p=list;
i=1;
while(p&&i<k)
{ r=p;
p=p->next;
++i;
}
for(i=1;i<n;i++)
{
for(j=1;j<m;j++)
{ r=p;
p=p->next;
}
printf("The out=%d\n",p->data);
r->next=p->next;
}
}
void main()
{
int x, y, z;
printf("input the lenth n\n");/*n,k,m分别代表总的人数,第一个报数的人,间隔的人数*/
scanf("%d",&x);
printf("input the start k\n");
scanf("%d",&y);
printf("input the m\n");
scanf("%d",&z);
JOSEPHU(x,y,z);
}
F. 求约瑟夫问题的C语言程序和流程图,程序用链表解决。麻烦帮忙一下吧!
这个问题用一维数组即可解决。
这是我自己写的一段代码:
//功能:解决约瑟夫问题
#include<stdio.h>
#define N 9
#define K 2
#define M 3
//给数组赋值
void setDate(int a[],int n)
{ int i;
for(i=0;i<n;i++)
a[i]=i+1;
}
//删除被选中的孩子
void deleted(int a[],int m,int len)
{
int i=m;
do
{
a[i]=a[i+1];
i++;
}while(i<len);
}
//开始play
void play(int a[],int k,int m)
{
int len =N;
int dm=k+m-2;//第一个被剔除的孩子
while(len!=1)
{printf("第%d个孩子被剔除。\n",a[dm]);
deleted(a,dm,len);//将被剔除的孩子从数组中删除
dm=dm+M-1;//下一个被剔除的孩子
len--;//数组的长度减1
if(dm>=len) dm=dm-len;
}
printf("最后一个孩子是%d.",a[0]);//最后一个孩子被放在a[0]中
}
main()
{
int a[N];
setDate(a,N);
play(a,K,M);
}
G. C语言中怎么用链表来表达约瑟夫问题
先创建n个人的环链表L,然后数数,每数a个数就干掉相应节点,再重新计数,直到最后剩下一个节点,就是所要求的结果
H. 怎样用C语言解决 "约瑟夫问题"
这是c++的,稍微修改一下就是c的程序了
#include <iostream.h>
#include <stdlib.h>
class CircList;
class CircListNode
{
friend class CircList;
public:
CircListNode(int d = 0, CircListNode *next = NULL)
: data( d ), link( next ) {}
int data;
CircListNode *link;
};
class CircList
{friend ostream & operator<<(ostream &, CircList &);
public:
CircList(int , int );
~CircList();
void MakeEmpty();
int getData() const;
void Remove();
void Insert(const int &);
void Next() { current = current->link; }
void Josephus();
private:
CircListNode *first, *current;
int person, recycle;
};
CircList ::CircList(int p, int r)
{
if(!p || !r)
{
cout<<"Error set for person and recycle!"<<endl;
exit(0);
}
person = p;
recycle = r;
current = first = new CircListNode(1, first);
if(p > 1)
{
int i = 1;
while(i++ < p)
Insert(i);
}
}
void CircList::Insert(const int & value)
{
current = current->link = new CircListNode(value, first);
}
void CircList ::MakeEmpty()
{
CircListNode *q;
while(first->link != first)
{
q = first->link;
first->link = q->link;
delete q;
}
}
int CircList::getData() const
{
return current->data;
}
void CircList::Remove()
{
if(first->link == first)
{
delete first;
exit(0);
}
CircListNode *q = first;
while(q->link != current)
q = q->link;
if(current == first)
{
q->link = first->link;
q = first;
current = first = first->link;
}
else
{
q->link = current->link;
q = current;
current = current->link;
}
delete q;
}
void CircList::Josephus()
{
current = first;
for(int i = 1; i <= person; i++)
{
for(int j = 1; j < recycle; j++)
Next();
cout<<"Delete person "<<getData()<<endl;
Remove();
// cout<<*this;
}
}
CircList::~CircList()
{
MakeEmpty();
delete first;
}
ostream & operator<<(ostream & output, CircList &c)
{
CircListNode *p = c.first;
cout<<"The list is :"<<endl;
for(; p->link != c.first; p = p->link)
cout<<p->data<<endl;
cout<<p->data<<endl;
return output;
}
int main(int argc, char* argv[])
{
CircList clist(9, 5);//共9个人,从第
//5个开始报数
clist.Josephus();
return 0;
}
I. (C语言)用静态链表求解约瑟夫问题。
#include
"stdio.h"
//
#include
"conio.h"
#include
"stdlib.h"
#define
MAX
100
typedef
struct
nodes
{
int
data;
nodes*
next;
}Lnode;
/*静态链表节点结构体定义
*/
//
typedef
struct
list
//
{
//
Lnode
node[MAX];
//
int
head;
//
}List,*PList;
void
InitList(Lnode*
pHead,int
n)/*n为节点数
*/
{
pHead->data
=
0;
Lnode*
pPre
=
pHead;
for(int
i=1;
i<n;
++i)
{
Lnode
*pTemp
=
(Lnode*)malloc(sizeof(Lnode));
pTemp->data
=
i;
pPre->next
=
pTemp;
pPre
=
pTemp;
if
(i
==
n-1)
{
pTemp
->next
=
pHead;
}
}
}
void
Searchnode(Lnode
*pHead,
int
n)/*m为报数,n为节点数,start为初始报数序号*/
{
Lnode*
pNext
=
pHead;
Lnode*
pPreNode
=
NULL;
while
(1)
{
for(int
i=0;
i<
n;
++i)
{
pPreNode
=
pNext;
pNext
=
pNext->next;
}
printf("delete:
%d
",pNext->data);
if
(pPreNode->next
==
pNext->next)
{
break;
}
pPreNode->next
=
pNext->next;
free((void
*)pNext);
pNext
=
pPreNode->next;
}
}
void
main()
{
int
i;
int
n=10,start=1;
Lnode*
pHeadNode
=
(Lnode*)malloc(sizeof(Lnode));
InitList(pHeadNode,
n);
Lnode*
pNext
=
pHeadNode;
for
(i=0;i<10;
++i)
{
printf("%d
",
pNext->data);
pNext
=
pNext->next;
}
printf("请输入一个数
");
scanf("%d",
&n);
n
%=
10;
Searchnode(pHeadNode,
n);
getchar();
//
printf("Hello,
world
");
}
J. c语言约瑟夫环问题 请大神给我详细讲解一下这个解法的思路 谢谢!
思路:
(1)
将n个人的编号(1,2,3,。。。,n)存入数组元素num[0],num[1],。。。,num[n-1]中。
程序段为:
p=num;
/***********SPACE***********/
for(i=0;i<n;i++)
/***********SPACE***********/
*(p+i)=i+1;
(2)
模拟报数(k++;),报到3 的人出圈(即对应的数组元素num[i]设置为0),并使出圈的人数+1(m++;),然后再从头报数,。。。,当出圈人数达到n-1时,报数结束。
程序段为:
i=0;
k=0;
m=0;
while(m<n-1)
{
/***********SPACE***********/
if(*(p+i)!=0) k++;
if(k==3)
{
*(p+i)=0;
k=0;
m++;
}
i++;
if(i==n) i=0;
}
(3)
此时,数组中不为0的那个元素的值就是后留下的那位的编号,找到它输出即可:
while(*p==0) p++;
printf("%d is left\n",*p);