线性表实验

  1. 窗口问题
    【问题描述】
    在某图形操作系统中,有N个窗口,每个窗口都是一个两边与坐标轴分别平行的矩形区域。窗口的边界上的点也属于该窗口。窗口之间有层次的区别,在多于一个窗口重叠的区域里,只会显示位于顶层的窗口里的内容。
    当你点击屏幕上一个点的时候,你就选择了处于被点击位置的最顶层窗口,并且这个窗口就会被移到所有窗口的最顶层,而剩余的窗口的层次顺序不变。如果你点击的位置不属于任何窗口,则系统会忽略你这次点击。
    现在我们希望你写一个程序模拟点击窗口的过程。
    【输入形式】
    输入的第一行有两个正整数,即N和M。(1≤N≤10,1≤M≤10)接下来N行按照从最下层到最顶层的顺序给出N个窗口的位置。每行包含四个非负整数x1,y1,x2,y2,表示该窗口的一对顶点坐标分别为(x1,y1)和(x2,y2)。保证x1<x2,y1<y2。
    接下来M行每行包含两个非负整数x,y,表示一次鼠标点击的坐标。题目中涉及到的所有点和矩形的顶点的x,y坐标分别不超过2559和1439。
    【输出形式】
    输出包括M行,每一行表示一次鼠标点击的结果。如果该次鼠标点击选择了一个窗口,则输出这个窗口的编号(窗口按照输入中的顺序从1编号到N);如果没有,则输出"IGNORED"(不含双引号)。
    【样例输入】
    3 4
    0 0 4 4
    1 1 5 5
    2 2 6 6
    1 1
    0 0
    4 4
    0 5
    【样例输出】
    2
    1
    1
    IGNORED
    【样例说明】
    第一次点击的位置同时属于第1和第2个窗口,但是由于第2个窗口在上面,它被选择并且被置于顶层。
    第二次点击的位置只属于第1个窗口,因此该次点击选择了此窗口并将其置于顶层。现在的三个窗口的层次关系与初始状态恰好相反了。第三次点击的位置同时属于三个窗口的范围,但是由于现在第1个窗口处于顶层,它被选择。
    最后点击的(0,5)不属于任何窗口。
    //我自己还添加了一些链表的其他算法,已经注释掉了,测试点都可以过。
#include <iostream>
#include <stdlib.h>
using namespace std;
typedef struct 
{
	int x1,y1;
	int x2,y2;
	int tag;
}LinkWindow;
typedef struct LNode
{
	LinkWindow data;
	struct LNode *next;
}LinkList;
LinkList *L;
int n,m;
void CreateListF(LinkList *&L)//头插法建立循环单链表 
{
	LinkList *s;
	int i;
	for(i=0;i<n;i++)
	{
		s=(LinkList *)malloc(sizeof(LinkList));
		cin>>s->data.x1>>s->data.y1>>s->data.x2>>s->data.y2;
		s->data.tag=i+1;
		s->next=L->next;
		L->next=s;
	}
}
void InitList(LinkList *&L)//初始化线性表 
{
	L=(LinkList *)malloc(sizeof(LinkList));
	L->next=NULL;
}
void DestroyList(LinkList *&L)//销毁线性表 
{
	LinkList *pre=L,*p=L->next;
	while(p!=NULL)
	{
		free(pre);
		pre=p;
		p=pre->next;
	}
	free(pre);
}
bool ListEmpty(LinkList *L)//判断线性表是否为空表 
{
	return (L->next==NULL);
}
int ListLength(LinkList *L)//输出线性表的长度 
{
	int t=0;
	LinkList *p=L;
	while(p->next!=NULL)
	{
		t++;
		p=p->next;
	}
	return (t);
}
void DispList(LinkList *L)//输出线性表 
{
	LinkList *p=L->next;
	while(p!=NULL)
	{
		cout<<p->data.tag<<" "<<"("<<p->data.x1<<","<<p->data.y1<<")"<<" "<<"("<<p->data.x2<<","<<p->data.y2<<")"<<endl;
		p=p->next;
	}
	cout<<endl;
}
bool GetElem(LinkList *L,int i,LinkWindow &e)//找到线性表中位置i的数据元素
{
	int j=0;
	LinkList *p=L;
	while(j<i&&p!=NULL)
	{
		j++;
		p=p->next;
	}
	if(p==NULL)
	return false;
	else
	{
		e=p->data;
		return true;
	}
} 
bool noequal(LinkList *p,LinkWindow e)
{
	if((p->data.x1!=e.x1)||(p->data.y1!=e.y1)||(p->data.x2!=e.x2)||(p->data.y2!=e.y2))
	return true;
	else return false;
}
int LocateElem(LinkList *L,LinkWindow e)//按元素值查找
{
	int i=1;
	LinkList *p=L->next;
	while(p!=NULL&&noequal(p,e))
	{
		p=p->next;
		i++;
	}
	if(p==NULL) return (0);
	else return (i);
} 
bool ListInsert(LinkList *&L,int i,LinkWindow e)//插入数据元素
{
	int j=0;
	LinkList *p=L,*s;
	while(j<i-1&&p!=NULL)
	{
		j++;
		p=p->next;
	}
	if(p==NULL) return false; 
	else
	{
		s=(LinkList *)malloc(sizeof(LinkList));
		s->data=e;
		s->next=p->next;
		p->next=s;
		return true;
	}
} 
bool ListDelete(LinkList *&L,int i,LinkWindow &e)//删除数据元素
{
	int j=0;
	LinkList *p=L,*q;
	while(j<i-1&&p!=NULL)
	{
		j++;
		p=p->next;
	}
	if(p==NULL) return false;
	else
	{
		q=p->next;
		if(q==NULL) return false;
		e=q->data;
		p->next=q->next;
		free(q);
		return true;
	}
} 
void DisWindow(LinkWindow e)
{
	cout<<e.tag<<" "<<"("<<e.x1<<","<<e.y1<<")"<<" "<<"("<<e.x2<<","<<e.y2<<")"<<endl;
}
void Click(LinkList *&L)
{
	int i;
	LinkList *p=L->next;
	LinkWindow e;
	for(i=0;i<m;i++)
	{
		p=L->next;
		int x,y,t;
		cin>>x>>y;
		while(p!=NULL)
		{
			if((x>=p->data.x1)&&(x<=p->data.x2)&&(y>=p->data.y1)&&(y<=p->data.y2))
		    break;
		    p=p->next;
		}
		if(p==NULL) cout<<"IGNORED"<<endl;
		else if(p!=L->next)
		{
			e=p->data;
			t=LocateElem(L,e);
			if(ListDelete(L,t,e))
			{
				if(ListInsert(L,1,e))
				cout<<e.tag<<endl;
			}
		}
		else if(p==L->next)
		{
			cout<<p->data.tag<<endl;
		}
	}
}
int main()
{
	LinkWindow e;
	cin>>n>>m;
	InitList(L);
	
	CreateListF(L);
	
	Click(L);
/*	DispList(L);
	
	if(ListEmpty(L)) cout<<"空表"<<endl;
	else cout<<"不为空表"<<endl;
	
	cout<<"链表长度为:"<<ListLength(L)<<endl;
	
	DispList(L);
	
	int t;
	cin>>t;//查找第t个元素的值 
	if(GetElem(L,t,e)) DisWindow(e);  
	else cout<<"false"<<endl;
	
	cin>>e.x1>>e.y1>>e.x2>>e.y2;//查找元素值为e的 
	cout<<LocateElem(L,e)<<endl; 
	
	cin>>t>>e.x1>>e.y1>>e.x2>>e.y2>>e.tag;
	if(ListInsert(L,t,e))//在第t个位置插入数据元素 
	cout<<"插入成功"<<endl;
	else  cout<<"插入失败"<<endl;
	cout<<"链表长度为:"<<ListLength(L)<<endl;
	DispList(L);
	
	cin>>t;//删除第t个位置的元素数据储存在e中 
	if(ListDelete(L,t,e)) cout<<"删除成功"<<endl;
	else cout<<"删除失败"<<endl;
	cout<<"链表长度为:"<<ListLength(L)<<endl;
	DispList(L);
	
	DestroyList(L);*/
	return 0;
}
  1. 约瑟夫(Joseph)问题
    【问题描述】
    约瑟夫(Joseph)问题的一种描述是:编号为1,2,3,…,n的n个人按顺时针方向围坐一圈,每人持有一个密码〈正整数〉,一开始任选一个正整数作为报数上限值m,从第一个人开始按顺时针方向自1开始顺序报数,报到m时停止报数,报m的人出列,将他的密码作为新的m值,从他在顺时针方向上的下一个人开始重新从1报数,如此下去,直至所有人全部出列为止。试设计一个程序求出出列顺序。
    基本要求:利用单向循环链表存储结构模拟此过程,按照出列的顺序打印出各人的编号。
    实现提示:程序运行后首先要求用户指定初始报数上限值,然后读取各人的密码(小于30)。
    【输入形式】
    输入包括两行,第一行包括报数上限值m和人数n,第二行为n个人的密码,所有数据之间由空格分隔。
    【输出形式】
    输出一行,共n个整数,表示各编号人的出列顺序。各数之间由空格分隔。
    【样例输入】
    20 7
    3 1 7 2 4 8 4
    【样例输出】
    6 1 4 7 2 3 5
#include <iostream>
#include <stdlib.h>
using namespace std;
typedef struct LNode
{
	int data;
	int tag;
	struct LNode *next;
}LinkList;
LinkList *L;
int m,n;//报数上限值m和人数n
void CreateListF(LinkList *&L)//尾插法建立循环单链表 
{
	LinkList *s,*r;
	int i;
	r=L;
	for(i=0;i<n;i++)
	{
		s=(LinkList *)malloc(sizeof(LinkList));
		cin>>s->data;
		s->tag=i+1;
		r->next=s;
		r=s;
	}
	r->next=L;
}
void InitList(LinkList *&L)//初始化线性表 
{
	L=(LinkList *)malloc(sizeof(LinkList));
	L->next=L;
}
void DestroyList(LinkList *&L)//销毁线性表 
{
	LinkList *pre=L,*p=L->next;
	while(p!=L)
	{
		free(pre);
		pre=p;
		p=pre->next;
	}
	free(pre);
}
bool ListEmpty(LinkList *L)//判断线性表是否为空表 
{
	return (L->next==L);
}
int ListLength(LinkList *L)//输出线性表的长度 
{
	int t=0;
	LinkList *p=L;
	while(p->next!=L)
	{
		t++;
		p=p->next;
	}
	return (t);
}
void DispList(LinkList *L)//输出线性表 
{
	LinkList *p=L->next;
	while(p!=L)
	{
		cout<<p->data<<" ";
		p=p->next;
	}
	cout<<endl;
}
bool GetElem(LinkList *L,int i,int &e)//找到线性表中位置i的数据元素
{
	int j=1;
	LinkList *p=L->next;
	while(j<i&&p!=L)
	{
		j++;
		p=p->next;
	}
	if(p==L)
	return false;
	else
	{
		e=p->data;
		return true;
	}
} 
int LocateElem(LinkList *L,int e)//按元素值查找
{
	int i=1;
	LinkList *p=L->next;
	while(p!=L&&p->data!=e)
	{
		p=p->next;
		i++;
	}
	if(p==L) return (0);
	else return (i);
} 
bool ListInsert(LinkList *&L,int i,int e)//插入数据元素
{
	int j=0;
	LinkList *p=L,*s;
	if(i==1)
	{
		s=(LinkList *)malloc(sizeof(LinkList));
		s->data=e;
		s->next=p->next;
		p->next=s;
		return true;
	}
	else
	{
		p=L->next;
		while(j<i-1&&p!=L)
		{
			j++;
			p=p->next;
		}
		if(p==L) return false; 
		else
		{
			s=(LinkList *)malloc(sizeof(LinkList));
			s->data=e;
			s->next=p->next;
			p->next=s;
			return true;
		}
	}
} 
bool ListDelete(LinkList *&L,int i,int &e)//删除数据元素
{
	int j=1;
	LinkList *p=L,*q;
	if(i==1)
	{
		q=L->next;
		e=q->data;
		L->next=q->next;
		free(q);
		return true;
	}
	else
	{
		p=L->next;
		while(j<i-1&&p!=L)
		{
			j++;
			p=p->next;
		}
		if(p==L) return false;
		else
		{
			q=p->next;
			if(q==L) return false;
			e=q->data;
			p->next=q->next;
			free(q);
			return true;
		}
	}
} 
void OutList(LinkList *&L)
{
	LinkList *p=L->next,*q;
	int i=1,e;
	while(1)
	{
		while(i<m)
		{
			if(p->next==L) p=L->next;
			else  p=p->next;
			i++;
		}
		cout<<p->tag<<" "; 
		if(p->next==L) q=L->next;
		else q=p->next; 
		int t=1;
		LinkList *s=L->next;
		while(s!=p)
		{
			s=s->next;
			t++;
		}
		if(ListDelete(L,t,e)) m=e;
		p=q;
		i=1;
		if(ListLength(L)==0) break;
	}
	cout<<endl;
}
int main()
{
	int e,t; 
	cin>>m>>n;
	InitList(L);
	CreateListF(L);
	OutList(L);
	/*if(ListEmpty(L)) cout<<"空表"<<endl;
	else cout<<"不为空表"<<endl;
	cout<<"链表长度为:"<<ListLength(L)<<endl;
	DispList(L);
	cin>>t;//查找第t个元素的值 
	if(GetElem(L,t,e)) cout<<e<<endl;  
	cin>>e;//查找元素值为e的 
	cout<<LocateElem(L,e)<<endl; 
	cin>>t>>e;
	if(ListInsert(L,t,e))//在第t个位置插入数据元素 
	cout<<"插入成功"<<endl;
	else  cout<<"插入失败"<<endl;
	cout<<"链表长度为:"<<ListLength(L)<<endl;
	DispList(L);
	cin>>t;//删除第t个位置的元素数据储存在e中 
	if(ListDelete(L,t,e)) cout<<"删除成功"<<endl;
	else cout<<"删除失败"<<endl;
	cout<<"链表长度为:"<<ListLength(L)<<endl;
	DispList(L);
	DestroyList(L);*/
	return 0;
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值