2015-08-12-数据结构Java实现(一)----算法概述

【声明】

欢迎转载,但请保留文章原始出处→_→

生命壹号:http://www.cnblogs.com/smyhvae/

文章来源:http://www.cnblogs.com/smyhvae/p/4724675.html

联系方式:[email protected]

【正文】

一、数据结构涵盖的内容:

二、算法的基本概念:

1、算法的概念:

Algorithm,是对特定问题求解步骤的一种描述,它是指令的有限序列,其中每一条指令表示一个或者多个操作。

2、算法的特性:

  • 有穷性:指令序列是有限的
  • 确定性:每条语句的含义明确,无二义性
  • 可行性:每条语句都应在有限的时间内完成
  • 输入:零个或者多个输入
  • 输出:一个或者多个输出

3、算法与程序的区别:

程序:

(program)程序是软件开发人员根据用户需求开发的、用程序设计语言描述的适合计算机执行的指令(语句)序列。

程序包含的四个要素:

数据结构

算法

程序设计方法

编程语言

程序与算法不同。程序是算法用某种程序设计语言的具体实现。程序可以不满足算法的有穷性,比如操作系统也是一种程序,如果你愿意,你的电脑可以一直开着,保持操作系统的运行。

比如:

  1. while(true)
  2. {
  3. ...
  4. }//是一段程序,但不是一个算法

4、程序、算法、软件之间的关系:

程序:算法的计算机实现。用某种编程语言实现。

算法:表示问题的解。

软件:程序+文档

如下图所示:

程序设计=数据结构+算 法

三、数据类型:

1、数据类型:

是指一个值的集合和定义在集合上的操作集合。例如:java的整数类型(Integer),就不仅仅表示整数数值的集合,还包括对整数类型进行的操作集合,加、减、乘、除、模等操作。

我们通常所指的数据类型是某种高级语言支持的基本数据类型。  比如java的基本数据类型:int、double、float、char等等。

Java中的数据类型:

2、抽象数据类型:

  一个数学模型以及定义在这个模型上的一组操作(由用户定义,用以表示应用问题的数据模型)。

看起来抽象数据类型和数据类型的定义基本相同。不同点在于:数据类型通常是指某种高级语言的,而抽象数据类型用户重新设计,一种概念。这里的"抽象"的含义在于数学抽象。

  • 原子类型:比如整型
  • 固定聚合类型:比如复数,两个实数确定的次序构成
  • 可变聚合类型:比如汽车类型,构成的成分是不确定的。(因为小轿车、大卡车的构成是不同的)

抽象数据类型抽象的层次越高,那么可复用性也越高。比如:java中的Object是对所有对象的抽象,那么就可以作为所有类的父类。

四、抽象数据类型的表示(代码举例):

  • C语言使用结构体
  • Java语言使用类

下面分别用C语言与java语言,来定义学生抽象数据类型。已知学生的信息如下:

  1. 学号:111222
  2. 姓名:生命壹号
  3. 性别:男
  4. 出生日期:1991-11
  5. 专业:电子与通信工程(计算机方向)
  6. 电子邮箱:[email protected].com

1、用C代码定义一个学生类:

test1.c:

  1. #include<stdio.h>
  2. //出生日期的结构体
  3. typedefstruct
  4. {
  5. int year;//年
  6. int month;//月
  7. int day;//日
  8. }Date;
  9. //学生结构体
  10. typedefstruct
  11. {
  12. char sid[20];//学号
  13. char name[20];//姓名
  14. char gender;//性别
  15. Date birthday;//出生日期
  16. char contact[50];//联系方式
  17. }Students;
  18. //打印学生信息
  19. voidPrintStudentsInfo(Students s)
  20. {
  21. printf("学号:%s\n",s.sid);
  22. printf("姓名:%s\n",s.name);
  23. printf("性别:%c\n",s.gender);
  24. printf("出生日期:%d-%d-%d\n",s.birthday.year,s.birthday.month,s.birthday.day);
  25. printf("联系方式:%s\n",s.contact);
  26. }
  27. int main()
  28. {
  29. Students s1;//生成一个学生对象
  30. Date d1;
  31. d1.year =1995;
  32. d1.month =6;
  33. d1.day =30;
  34. strcpy(s1.sid,"S0001");
  35. strcpy(s1.name,"张三丰");
  36. strcpy(s1.contact,"西安市高新四路50号");
  37. s1.gender =‘M‘;
  38. s1.birthday = d1;
  39. PrintStudentsInfo(s1);
  40. getch();
  41. return0;
  42. }

运行效果:

2、用Java代码定义一个学生类:

(1)Student.java:

  1. package test1;
  2. import java.text.SimpleDateFormat;
  3. import java.util.Date;
  4. /**
  5. * Created by smyhvae on 2015/8/12.
  6. */
  7. publicclassStudent{
  8. String num;//学号
  9. String name;//姓名
  10. char sex;//性别
  11. Date birthday;//出生日期
  12. String contact;//联系方式
  13. publicString getNum(){
  14. return num;
  15. }
  16. publicvoid setNum(String num){
  17. this.num = num;
  18. }
  19. publicString getName(){
  20. return name;
  21. }
  22. publicvoid setName(String name){
  23. this.name = name;
  24. }
  25. publicchar getSex(){
  26. return sex;
  27. }
  28. publicvoid setSex(char sex){
  29. this.sex = sex;
  30. }
  31. publicDate getBirthday(){
  32. return birthday;
  33. }
  34. publicvoid setBirthday(Date birthday){
  35. this.birthday = birthday;
  36. }
  37. publicString getContact(){
  38. return contact;
  39. }
  40. publicvoid setContact(String contact){
  41. this.contact = contact;
  42. }
  43. @Override
  44. publicString toString(){
  45. SimpleDateFormat sdf =newSimpleDateFormat("YYYY-mm-dd");//将Date日期转化为String字符串打印出来
  46. return"Student{"+
  47. "num=‘"+ num +‘\‘‘+
  48. ", name=‘"+ name +‘\‘‘+
  49. ", sex="+ sex +
  50. ", birthday="+ sdf.format(birthday)+
  51. ", contact=‘"+ contact +‘\‘‘+
  52. ‘}‘;
  53. }
  54. }

(2)JavaTest.java:(给学生类赋值并打印出来)

  1. package test1;
  2. import java.text.ParseException;
  3. import java.util.Calendar;
  4. import java.util.Date;
  5. /**
  6. * Created by smyhvae on 2015/8/12.
  7. */
  8. publicclassJavaTest{
  9. publicstaticvoid main(String[] args)throwsParseException{
  10. Student s =newStudent();
  11. s.setNum("111222");
  12. s.setName("生命壹号");
  13. s.setSex(‘男‘);//这里面赋值可以用中文
  14. s.setContact("[email protected]");
  15. Calendar calendar =Calendar.getInstance();
  16. calendar.set(1991,11,28);
  17. Date date = calendar.getTime();
  18. s.setBirthday(date);
  19. System.out.println(s.toString());
  20. }
  21. }

运行效果如下:

五、算法的设计目标:

1、算法的设计目标:

(1)正确性:满足具体问题的解,基本目标。

(2)可读性:有利于人去理解算法。

(3)健壮性:输入非法数据,能适当做出处理,不产生莫名其妙的输出。

(4)高效性:包括时间的高效性(时间复杂度)和空间的高效性(空间复杂度)。

2、算法性能指标:

(1)算法的时间效率也称为时间复杂度。

(2)算法的空间效率也称为空间复杂度。

(3)同一问题可用不同算法解决,而一个算法的质量优劣将影响到算法乃至程序的效率。算法分析的目的在于选择合适算法和改进算法。一个算法的评价主要从时间复杂度和空间复杂度来考虑

(4)算法时间的高效性和空间的高效性通常是矛盾的。所有一般只会取一个平衡点。(这里体现的是一种哲学思想,研究计算机,不就是研究时间和空间的概念嘛,鱼与熊掌不可兼得哦)

(5)通常我们假设程序运行在内存中,且内存容量足够使用,所以更多的是讨论时间复杂度。

六、算法的时间复杂度:

算法的时间复杂度反映了算法执行的时间长短。度量一个算法在计算机上执行的时间通常有两种方式:

1.事后统计法:

2.事前分析法:(常用)

编写算法使用的高级语言

编程产生的机器语言代码质量

机器指令执行速度

问题规模

注:算法的时间复杂度是由最深层嵌套语句的频度决定的。

2、O()函数:

表示算法的时间效率与算法所处理的数据元素个数n函数关系的最常用函数,即O()函数。

定义:

一般情况下,算法中基本操作重复执行的次数是问题规模n的某个函数,用T(n)表示,若有某个辅助函数f(n),使得当n趋近于无穷大时,T(n)/f(n)的极限值为不等于零的常数,则称f(n)是T(n)的同数量级函数。记作T(n)=O(f(n)),称O(f(n)) 为算法的渐进时间复杂度,简称时间复杂度。看下图便知:

情况一:T(n)与问题规模n无关

当算法的时间复杂度T(n)与问题规模n无关时,此时算法的时间复杂度T(n)=O(1)。例如:计算下列算式的前N项和。

1-2+3-4+5.....+N

分析:当N为奇数时,和为:(N+1)/2

当N为偶数时,和为:-N/2

情况二:T(n)与问题规模n有关

例1:设数组a和b在前面部分已经赋值,求如下两个n阶矩阵相乘算法的时间复杂度:

  1. for(i=0;i<n;i++)
  2. {
  3. for(j=0;j<n;j++)
  4. {
  5. c[i][j]=0;//基本语句1
  6. for(k=0;k<n;k++)
  7. {
  8. c[i][j]=c[i][j]+a[i][k]*b[k][j];//基本语句2
  9. }
  10. }
  11. }

上方代码中:

例2:设n为如下算法处理的数据元素个数,求算法时间复杂度。代码如下:

  1. for(i=1;i<=n;i=i*2)
  2. {
  3. System.out.println(i);
  4. }

分析:

例3:分析冒泡排序算法的时间复杂度。代码如下:

  1. //冒泡排序算法
  2. publicstaticvoid bubbleSort(int[] data){
  3. if(data ==null){
  4. return;
  5. }
  6. for(int i =0; i < data.length -1; i++){
  7. boolean flag =false;
  8. for(int j =0; j < data.length -1- i; j++){
  9. if(data[j]> data[j +1]){
  10. int temp = data[j];
  11. data[j]= data[j +1];
  12. data[j +1]= temp;
  13. flag =true;
  14. }
  15. }
  16. if(!flag){
  17. return;
  18. }
  19. }
  20. }

时间复杂度分析:

(1)最佳情况下,冒泡排序算法只需要遍历一次就能确定数组已经排序好了,此时的时间复杂度为O(n);

(2)最差情况下,需要进行n-1次遍历,则需进行n(n-1)/2次比较和记录移动,此时冒泡排序算法的时间复杂度T(n)=O(n2)。

3、时间复杂度的大小关系:

以下六种计算算法时间的多项式是最常用的。其关系为:

指数时间的关系为:

当n取很大的值时,指数时间算法和多项式时间算法在所需时间上非常悬殊。

小知识:

NP(nondeterministic polynomial)问题:是指算法复杂度难以用多项式表示的问题,算法复杂度通常是n的指数级,常规算法很难求解。

七、算法的空间复杂度:

空间复杂度是指算法在运行期间所需要的内存空间的数量级。记作:S(n)=O(f(n)),其中n为问题的规模(或大小)。

注:由于大部分算法的空间复杂度问题并不严重,并且算法的空间复杂度分析方法和算法的时间复杂度分析方法基本相同,所以一般数据结构只讨论算法的时间复杂度,不讨论算法的空间复杂度。

代码举例:分析如下算法的空间复杂度

  1. staticvoid reserse(int[] a,int[] b)
  2. {
  3. int n= a.length;
  4. for(int i=0;i<n;i++)
  5. {
  6. b[i]=a[n-1-i];
  7. }
  8. }

上方代码中,当程序调用reserse(a,b)函数时,要分配的内存空间包括:引用a,引用b,局部变量n和局部变量i;

因此f(n)=c;其中c为常量。所以该算法的空间复杂度S(n)=O(1)。

八、总结:

算法的时间复杂度和两个因素有关:算法中的最大嵌套循环层数;最大嵌套循环结构中每次循环的次数。

一般来说,具有多项式时间复杂度的算法是可以接受的;具有指数(不是对数)时间复杂度的算法,只有当n足够小时才可以使用。一般效率较好的算法要控制在O(N)或者O(log2 N)

时间: 2024-11-06 07:21:17

2015-08-12-数据结构Java实现(一)----算法概述的相关文章

【软帝学院】12道java经典入门算法题!

12道java经典入门算法题! [程序1]   题目:将一个数组逆序输出. 程序分析:用第一个与最后一个交换. 其实,用循环控制变量更简单: for(int k=11;k>=1;k--) System.out.print(myarr[k]+","); [程序2]   题目:取一个整数a从右端开始的4-7位. 程序分析:可以这样考虑: (1)先使a右移4位. (2)设置一个低4位全为1,其余全为0的数.可用~(~0 < <4) (3)将上面二者进行&运算. pu

12道java经典入门算法题!

12道java经典入门算法题![程序1] ? 题目:将一个数组逆序输出. ? 程序分析:用第一个与最后一个交换. ? 其实,用循环控制变量更简单:for(int k=11;k>=1;k--)System.out.print(myarr[k]+","); [程序2] ? 题目:取一个整数a从右端开始的4-7位. ? 程序分析:可以这样考虑: ? (1)先使a右移4位. ? (2)设置一个低4位全为1,其余全为0的数.可用~(~0 < <4) ? (3)将上面二者进行&a

Storm(2015.08.12笔记)

2015.08.12Storm ? 一.Storm简介 Storm是Twitter开源的一个类似于Hadoop的实时数据处理框架. ? Storm能实现高频数据和大规模数据的实时处理. 官网资料显示storm的一个节点在1秒钟能够处理100万个100字节的消息([email protected]的CPU,24GB的内存) (storm +kafka+flume) ? ? 二.HADOOP与STORM比较 数据来源:HADOOP处理的是HDFS上TB级别的数据(历史数据),STORM是处理的是实时

数据结构Java实现(一)----算法概述

[声明] 欢迎转载,但请保留文章原始出处→_→ 生命壹号:http://www.cnblogs.com/smyhvae/ 文章来源:http://www.cnblogs.com/smyhvae/p/4724692.html 联系方式:[email protected] [正文] 一.数据结构涵盖的内容: 二.算法的基本概念: 1.算法的概念: Algorithm,是对特定问题求解步骤的一种描述,它是指令的有限序列,其中每一条指令表示一个或者多个操作. 2.算法的特性: 有穷性:指令序列是有限的

(2)Java数据结构--二叉树 -和排序算法实现

=== 注释:此人博客对很多个数据结构类都有讲解-并加以实例 Java API —— ArrayList类 & Vector类 & LinkList类Java API —— BigDecimal类Java API —— BigInteger类Java API —— Calendar类Java API —— DateFormat类Java API —— Date类Java API —— HashMap类 & LinkedHashMap类Java API —— JDK5新特性Java

Java数据结构 遍历 排序 查找 算法实现

1. 遍历算法(遍历二叉树6种方法) 1.1. 概述 遍历算法针对二叉树而言的,主要有先序.中序.后序三种遍历顺序,三种顺序又分别有递归和常规算法,二叉树遍历的主要思想是:遍历左子树,遍历右子树,访问根节点,由这三者的遍历顺序来确定是先序.中序还是后序.下面只要求掌握递归遍历算法,常规遍历算法见附录一. 1.2. 先序遍历算法 遍历顺序:访问根节点,遍历左子树,遍历右子树.代码如下: void preOrder(BinaryTreeNode bt) { if (bt == null)// 如果当

JAVA 图作业算法实现、代写Graphs 数据结构作业

JAVA 图作业算法实现.代写Graphs 数据结构作业Lab Case – Algorithms and Data Structure, 2017-2018Phase 3. GraphsCurrently, SharingCar only provides service in ten cities (Madrid, Barcelona, Valencia, Sevilla, Bilbao, Granada, Toledo, Salamanca, Alicante, Cáceres). Not

12道Java算法与编程面试题

12道Java算法与编程面试题自己整理的面试题,希望可以帮到大家,需要更多资料的可以私信我哦,大家一起学习进步! 算法与编程1.编写一个程序,将a.txt文件中的单词与b.txt文件中的单词交替合并到c.txt文件中,a.txt文件中的单词用回车符分隔,b.txt文件中用回车或空格进行分隔.答:package cn.itcast; import java.io.File;import java.io.FileReader;import java.io.FileWriter; public cla

数据结构Java实现06----中缀表达式转换为后缀表达式

数据结构Java实现06----中缀表达式转换为后缀表达式 本文主要内容: 表达式的三种形式 中缀表达式与后缀表达式转换算法 一.表达式的三种形式: 中缀表达式:运算符放在两个运算对象中间,如:(2+1)*3.我们从小做数学题时,一直使用的就是中缀表达式. 后缀表达式:不包含括号,运算符放在两个运算对象的后面,所有的计算按运算符出现的顺序,严格从左向右进行(不再考虑运算符的优先规则),如:2 1 + 3 *.又比如3+(6-4/2)*5=23的后缀表达式为:3642/-5*+# (#符号为结束符

数据结构Java实现03----单向链表的插入和删除

数据结构Java实现03----单向链表的插入和删除 文本主要内容: 链表结构 单链表代码实现 单链表的效率分析 一.链表结构:            概念: 链式存储结构是基于指针实现的.我们把一个数据元素和一个指针称为结点.   数据域:存数数据元素信息的域. 指针域:存储直接后继位置的域. 链式存储结构是用指针把相互直接关联的结点(即直接前驱结点或直接后继结点)链接起来.链式存储结构的线性表称为链表. 链表类型: 根据链表的构造方式的不同可以分为: 单向链表 单向循环链表 双向循环链表 二