第八章学习小结

第八章数据结构小结
数据结构这一章主要讲的是关于排序的各种方法,由于不同应用对于时间复杂度与空间复杂度的要求不同,用的排序方法也不同,主要的排序方法有插入排序,交换排序,选择排序与归并排序,其中插入排序分为直接插入排序,间接插入排序与希尔排序,交换排序分为冒泡排序与快速排序,选择排序分为简单选择排序与堆排序,而归并排序则主要用于两个有序表的合成。以上的排序方法都属于是内部排序,而对于一些更大量的数据就要涉及到外部排序,下面是关于排序的应用习题。


给定公司N名员工的工龄,要求按工龄增序输出每个工龄段有多少员工。

输入格式:

输入首先给出正整数N(≤10?5??),即员工总人数;随后给出N个整数,即每个员工的工龄,范围在[0, 50]。

输出格式:

按工龄的递增顺序输出每个工龄的员工个数,格式为:“工龄:人数”。每项占一行。如果人数为0则不输出该项。

输入样例:

8
10 2 0 5 7 2 5 2

输出样例:

0:1
2:3
5:2
7:1
10:1

这道题属于排序应用中的简单题,只要用简单的冒泡排序加上输出的要求即可通过。
#include <iostream>
using namespace std;

int main()
{
	int worktime[51]={0};	//定义一个数组(下标为工龄)来表示不同工龄的人数 

	int n;	//定义参数 

	cin>>n;	//输入人数 

	int a[n];	//定义一个数组存储输入的工龄 

	int i;	//定义参数 

	for(i=0;i<n;i++)	//循环输入
	{
		cin>>a[i];	//输入工龄
		worktime[ a[i] ]++;	//相应工龄的人数+1
	}

	for(i=0;i<=50;i++)	//循环判断
	{
		if(worktime[i]!=0)	//若该工龄人数不为0
		{
			cout<<i<<":"<<worktime[i]<<endl;	//输出
		}
	}

	return 0;
}

下面再来看一道比较难的题目。



计算机程序设计能力考试(Programming Ability Test,简称PAT)旨在通过统一组织的在线考试及自动评测方法客观地评判考生的算法设计与程序设计实现能力,科学的评价计算机程序设计人才,为企业选拔人才提供参考标准(网址http://www.patest.cn)。

每次考试会在若干个不同的考点同时举行,每个考点用局域网,产生本考点的成绩。考试结束后,各个考点的成绩将即刻汇总成一张总的排名表。

现在就请你写一个程序自动归并各个考点的成绩并生成总排名表。

输入格式:

输入的第一行给出一个正整数N(≤100),代表考点总数。随后给出N个考点的成绩,格式为:首先一行给出正整数K(≤300),代表该考点的考生总数;随后K行,每行给出1个考生的信息,包括考号(由13位整数字组成)和得分(为[0,100]区间内的整数),中间用空格分隔。

输出格式:

首先在第一行里输出考生总数。随后输出汇总的排名表,每个考生的信息占一行,顺序为:考号、最终排名、考点编号、在该考点的排名。其中考点按输入给出的顺序从1到N编号。考生的输出须按最终排名的非递减顺序输出,获得相同分数的考生应有相同名次,并按考号的递增顺序输出。

输入样例:

2
5
1234567890001 95
1234567890005 100
1234567890003 95
1234567890002 77
1234567890004 85
4
1234567890013 65
1234567890011 25
1234567890014 100
1234567890012 85

输出样例:

9
1234567890005 1 1 1
1234567890014 1 2 1
1234567890001 3 1 2
1234567890003 3 1 2
1234567890004 5 1 4
1234567890012 5 2 2
1234567890002 7 1 5
1234567890013 8 2 3
1234567890011 9 2 4

分析一下这道题目,题目要求求出考生总的排名以及在考点的排名,由于1个考点人数最多只有300人,用冒泡排序解决没什么大问题,但是在总的排序中如果使用冒泡排序,时间复杂度会大大提高,就会出现运行超时的情况,最后一个测试点会通不过,对于大的数据量我这里采用的是快速排序,相比于O(n^2),O(nlog2n)明显就缩小了运行时间很多,下面分享一下我的代码(代码较长,可能需要改进)。
#include <iostream>
using namespace std;

typedef struct //定义考生结构体
{
	int address;	//考点
	int score;		//分数
	int rank;		//考点排名
	int allrank;	//总排名
	string num;		//学号
}student;

int partition(student a[], int left, int right)	//快速排序一,用于总考生的分数排序 

{
	int i = left;	//枢轴为最左侧
	student temp;	//定义一个结构体用于交换 

	for (int j = left; j < right; j++)	//快速排序
	{
		if (a[j].score > a[left].score)
		{
			++i;
			temp=a[i];a[i]=a[j];a[j]=temp;
		}
	}

	temp=a[i];a[i]=a[left];a[left]=temp;

	return i;	//返回枢轴
}

int ex_partition(student a[], int left, int right)	//快速排序二,用于总考生的相同分数的学号排序 

{
	int i = left;	//枢轴为最左侧
	student temp;	//定义一个结构体用于交换 

	for (int j = left; j < right; j++)////快速排序
	{
		if (a[j].num < a[left].num)
		{
			++i;
			temp=a[i];a[i]=a[j];a[j]=temp;
		}
	}

	temp=a[i];a[i]=a[left];a[left]=temp;

	return i;	//返回枢轴
}

void Qsort(student a[],int left,int right)	//快速排序一的递归
{
	if(left<right)	//若排序划分未进行到底
	{
		int mid=partition(a,left,right);	//获取枢轴
		Qsort(a,left,mid);	//左子表快速排序
		Qsort(a,mid+1,right);	//右子表快速排序
	}
}

void ex_Qsort(student a[],int left,int right)	//快速排序二的递归
{
	if(left<right)	//若排序划分未进行到底
	{
		int mid=ex_partition(a,left,right);	//获取枢轴
		ex_Qsort(a,left,mid);	//左子表快速排序
		ex_Qsort(a,mid+1,right);	//右子表快速排序
	}
}

int find(student a[],int s,int r)	//快速排序二中寻找相同分数考生的函数
{
	while(s!=r-1 && a[s].score==a[s+1].score)s++;	//若与下一个考生分数相同,且不为最后一个(防止段错误),参数+1 

	return s+1;	//返回值
}

int main()
{
	int i,j,k,l,p,q;	//定义参数 

	k=0;	//参数置0 

	student a[30000];	//定义最大要求的结构体数组 

	student temp;	//定义一个结构体用于交换 

	int	n1,n2;	//定义参数表示考点数与考点考生数 

	cin>>n1;	//输入考点数 

	for(i=0;i<n1;i++)
	{
		cin>>n2;	//输入考点考试数 

		l=k;	//记录当前k值 

		for(j=0;j<n2;j++)
		{
			cin>>a[k].num>>a[k].score;	//记录考试学号及分数
			a[k].address=i+1;	//记录考生考点
			k++;
		}

		for(p=l;p<k;p++)	//同一考点考生分数排序 (最大考生数为300,冒泡排序即可)
		{
			for(q=l;q<k;q++)
			{
				if(a[p].score>a[q].score)
				{
					temp=a[q];a[q]=a[p];a[p]=temp;
				}
			}
		}

		for(p=l;p<k;p++)	//同一考点考生排名
		{
			if(p!=l && a[p].score==a[p-1].score)a[p].rank=a[p-1].rank;	//若考生不为该考点第一个人,且分数与下一个人相同,则排名与上一个人相同
			else a[p].rank=p-l+1;	//分数不同,正常排名
		}
	}

	int number=k;	//记录总考生人数 

	Qsort(a,0,number);	//总体按分数快速排序 (快速排序一) 

	k=0;	//k置0 

	while(k<number)	//若考生未排序完
	{
		l=k;	//记录k值
		k=find(a,k,number);	//获取分数相同考生位置
		ex_Qsort(a,l,k);	//根据学号快速排序(快速排序二)
	}

	for(i=0;i<number;i++)	//总排名
		{
			if(i!=0 && a[i].score==a[i-1].score)a[i].allrank=a[i-1].allrank;	//若考生不为第一个人,且分数与下一个人相同,则排名与上一个人相同
			else a[i].allrank=i+1;	//分数不同,正常排名
		}

	//输出 

	cout<<number<<endl;	//输出总人数 

	for(i=0;i<number;i++)
	{
		cout<<a[i].num<<" "<<a[i].allrank<<" "<<a[i].address<<" "<<a[i].rank<<endl;	//按照格式输出学号,总排名,考点,考点排名
	}

	return 0;
}

以上,就是本人对于排序这一章的学习小结,如有错误,还请指出。

原文地址:https://www.cnblogs.com/xiedehan/p/10989497.html

时间: 2024-08-08 14:05:48

第八章学习小结的相关文章

git学习小结

背景:最近因为工作原因,需要将以前的代码库由bitbucket重新布置在一台服务器上,所以就学习了下git,特此记录下 在167这台机器上搭建apache,用做git server,由于以前apache都已经搭好了,所以这里只配置git server 就可以了,此处贴出配置: 服务器搭好了,来到配置中的root目录,git clone https://[email protected]/XXXX 此时,库和服务器都搭好了,用于新库测试的机器也可以从git server上克隆库了,来,我们来试试从

网络编程学习小结

几种网络编程方式: ISAPI.CGI.WinInet.Winsock 它们之间的差别: 1)  ISAPI主要是开发基于浏览器client与server端程序.效率比CGI方式高,并且也扩展了CGI没有的一些功能.(基于TCP/IP模型中的应用层) 2)  CGI主要是开发基于浏览器client与server端程序.(基于TCP/IP模型中的应用层) 3)  WinInet主要是开发client程序.(基于TCP/IP模型中的应用层) 4)  Winsock主要是基于socket来开发clie

MogileFS学习小结

大纲: 一.关于MogileFS 二.常见分布式文件系统 三.MogileFS基本原理 四.MogileFS的实现 一.关于MogileFS 当下我们处在一个互联网飞速发展的信息社会,在海量并发连接的驱动下每天所产生的数据量必然以几何方式增长,随着信息连接方式日益多样化,数据存储的结构也随着发生了变化.在这样的压力下使得人们不得不重新审视大量数据的存储所带来的挑战,例如:数据采集.数据存储.数据搜索.数据共享.数据传输.数据分析.数据可视化等一系列问题. 传统存储在面对海量数据存储表现出的力不从

201671010130 2016-2017-2 《Java程序设计》第四周学习小结

第四周学习小结 本次实验巩固了上次实验分隔数并求和的题,目前这个题有两种做法,一种是不断对数10求余,余数保存在sum中,然后左移一位,直到余数为零.另一种就是将数字强制转换成一个字符串数组String s=String.valueOf(num),根据方法s.toCharArray()将字符分离出来,据"x"-"0"=x,unicode码值相减即可得x的值. 父类和子类能够看两个交集,super关键字是否能够看做一个子类和超类的接口呢? 在子类中可以增加域.增加方法

初识ASP.NET---点滴的积累---ASP.NET学习小结

差不多十多天前学习完了北大青鸟的学习视频,没想到没几天的时间就看完了XML视频和牛腩的Javascript视频.学习完了也该总结总结,理理自己的思路,消化一下自己学习到的东西. 视频中的理论知识并不是很多,以例子驱动学起来也不会他过于乏味.全部的学习内容大概的可以用下图表示. 个人感觉这套视频的体系感不是很强,每一集之间老师的串联并不是做得很好,向我等没有教材的有些小的知识无从知晓.但是不能不说这套视频确很适合初学者学习,老师讲解的也不错,从此我也算是入门. 当然要想进一步的了解ASP.NET并

8086汇编学习小结———实时更新

初学IBM-PC 8086,对INT指令不是很理解.现从网上总计如下: 表:DOS系统功能调INT 21H AH 功能 调用参数 返回参数 00 程序终止(同INT 20H) CS=程序段前缀 01 键盘输入并回显 AL=输入字符 02 显示输出 DL=输出字符 03 异步通迅输入 AL=输入数据 04 异步通迅输出 DL=输出数据 05 打印机输出 DL=输出字符 06 直接控制台I/O DL=FF(输入)DL=字符(输出) AL=输入字符 07 键盘输入(无回显) AL=输入字符 08 键盘

《Pro AngularJS》学习小结-01

<Pro AngularJS>该书以一个SportsStore案例为主线铺开. 一.开发环境设置 该书中所用的server开发环境是Deployed,从来没听说过,而且作者也说该server没什么人用,我干脆弃用之.其他的环境包括 NodeJS--这个必须装 karma--测试环境,前期还没有用到,以后认真研究,毕竟AngularJS一大特点是Unit Test bootstrap--这个现在应该普遍使用了,O(∩_∩)O webstorm--现在唯一支持AngularJS插件的IDE 我基本

自动化测试Selenium Webdriver (JAVA)学习小结

自动化测试--Selenium学习小结 一.自动化测试的概念及意义: 1.什么是自动化测试: 一般是指软件测试的自动化,软件测试就是在预设条件下运行系统或应用程序,评估运行结果,预先条件应包括正常条件和异常条件. 2.意义: 让测试更有效率,利用更多的空余时间,减少人力资源. 二.selenium工具 我用的是java语言,所以接下来的例子和方法都是基于java的. 1.环境配置 (1)Jdk的配置: 我用的是1.7的jdk,配置方法都一样,新建一个JAVA_HOME,把你装好的jdk的路径复制

点滴的积累---J2SE学习小结

点滴的积累---J2SE学习小结 什么是J2SE J2SE就是Java2的标准版,主要用于桌面应用软件的编程:包括那些构成Java语言核心的类.比方:数据库连接.接口定义.输入/输出.网络编程. 学习感受 近半个月的坎坷,总算是将马士兵的<J2SE教程>视频看完了,期间一些其它的事一些不得不处理的事总是打断我的安排.看了视频之后认为东西确实都非常基础给我印象最深的是关于程序执行的内存分析.IO和线程,这谁在之前不管是学习VB.VB.NET还是C#中都没怎么设计到的东西. 首先,我想对于一个初学