20202322 2020-2021-2《数据结构与面向对象程序设计》课程总结

 

一、课程内容总结(课上做的笔记。自己纯手打的,剔除了错别字,年代久远不知道是不是课上抄的ppt,但是一定是自己纯手打的!而且没有标章节我就按照课程教学和笔记分章节了)(写着写着发现我的有些笔记好像丢了,靠)

 

第一章 编程语言

Java是一种面向对象的编程语言。
1.编译:编译器把源代码直接转换成某一特定的目标代码。执行时无需再编译。执行速度快。但被编译成热定的机器语言,所以无法在不同的机器上执行。
   解释:执行前不转换,执行时一边解释一边执行。执行速度慢,执行前未被编译,只要平台上有适当的解释器,就能被执行。

2.Java应用程序基本结构
//comments about the class
public class MyProgram (类名单词首字母大写,文件名同主类名)
{
(class body)
}

一个简单的java程序例子:
public class HelloWorld
{
public static void main(String []args)
{
System.out.println("Hello World!");
}
}

3.Java注释
标识符:编程人员在程序中使用的单词。Java中的标识符由字母数字下划线等等组成,对大小写字母敏感。

空格符:包括空格、tab、回车换行符。作为单词和符号的分隔符,不影响程序的执行。一个有效的程序可以有多重书写格式。

自增自减运算符、赋值运算符。temp++与++temp取值时无区别。 -= *= /= %=a%=b a+=b:a=a+b

4.java四种数据转换类型:数据类型转换、赋值类型转换、提升类型转换、强制类型转换

5.类与对象(类=属性【变量,对象】+方法【函数】)
String类、包装器类、枚举类、Math类、Random类等等,静态类与非静态类,


 

第二章 类Class与对象Object

1.类是对象的蓝图

   类:属性(变量/对象 虽然并不准确)+方法(操作/函数 函数也不准确,而且方法就是操作啦)
   类的分析:
   举例:Animal:

  //类1:
public class Animal
{
public String name;
String number;
private float weight;

public Animal(){
name = "";
number = "20202300";
weight = 0;
class1 = "2023";
}
public void setName(String Aname){
name = Aname;
}
public void setNumber(String Anumber){
number = Anumber;
}
public void shout(){
System.out.println("shout!");
}
public void eat(){
System.out.println("eat food");
}
public void setWeight(float Aweight){
weight = Aweight;
}
private float getWeight(){
int nothing = 0;
System.out.println("weight:”+weight);
return weight;
}
}


  //类2:
public class AnimalTest
{
public static void main(String []args){
Animal animal1 = new Animal();
Animal animal2 = new Animal();
animal1.setName("daju");
animal1.setNumber("20202300");
animal1.shout();
animal1.eat();
animal1.setWeight(200);
System.out.println("daju's weight:"+animal1.weight);
System.out.println(animal1.class1);
System.out.println(animal2.class2);
}
}

   属性:名称、类型、性别、体重、喜好......
   方法:跑、吃、叫......

普通类
接口类:属性(常量)+方法(全部都是且只能是抽象方法abstract) 必须实现所有的抽象方法(abstract可有可无,但需要implements)
抽象类:属性(变量、常量、对象)+方法(抽象、非抽象方法、也可以没有!!)
继承:extends,父类、子类,super/this
重写:重写父类的方法
重载:方法(不同参数、参数的个数、参数的类型)
多态:多种形态,父类的对象指向子类的对象,调用子类的方法(类继承、接口)
*(1)抽象类必须使用abstract明确声明;
 (2)如有抽象类里的方法必须使用abstract进行明确声明;
 (3)抽象类里也可以没有方法;
 (4)实现抽象方法使用extends关键字;
 (5)抽象类不能实例化instantiated。


2.方法的定义:可选的修饰符、返回值类型、制定方法名的标识符、参数列表和方法体。

-public:可见性修饰符号
-static:静态方法 虚拟机访问该方法 不需要实例化类对象
-main:方法名的标识符
--中括号:参数
--花括号:方法体

构造函数(构造方法!)
-与类名相同
-无返回值类型

3.面向对象——OPP三要素:封装、继承、多态*
public class ClassName{
//1.属性
int Varl;
Book a;
//2.方法
eat( );
}

封装Encapsulation:类外部的代码难于访问和修改类内部的变量,该特性称为“封装”。
见性修饰符:Public(可在外部访问)、Private(只能在内部访问)、protected

继承:Object类(万类之祖)

多态:

public class Animal {
public static void main(String[] args) {

//多态
Animal2023 animal2023 = dog2023;
animal2023.shout();
animal2023.feed("bone and shit");
animal2023 = daju2023;
animal2023.shout();
aniaml2023.feed("dog's shit");
}
}


4.软件开发(程序)

 

 

程序=数据结构+算法软件=程序+软件工程
开发教务管理系统:需求(选课/查成绩/评价/毕业设计/大创项目)、设计(例如UML类图及关系)、编程实现、测试(Animal类、AnimalTest类)
确定软件需求>软件设计>实现软件设计>软件测试
(1)伪代码: if num>0 正整数; if num<0 负整数
(2)产品代码
    class Student{
    ......
    }
(3)测试代码
    StudentTester{
    main
    }

5.类间关系

(1)依赖:类A的方法需使用类B的方法。AnimalTest>Animal
  静态方法:在A中直接使用B.xxxx()
  非静态方法:在A中,需要实例化B。 b = new B(); b.xxxx
(2)聚合:has-a关系。聚合关系是依赖关系的特殊类型。
  例如:汽车由发动机、底盘、车轮和其他部件组成。this引用:本对象。
  除此之外还有组合、继承、关联等。

 

第三章 查找

查找定义:也叫检索,是根据给定的某个值,在表中确定一个关键字等于给定值的记录或数据元素。

常用方法:线性查找、二分查找法、分块查找法、索引查找法。

1.方法1:线性查找(顺序查找)(顺序+链式)
-适用于小型和(或)没有排序的线性表
-用关键字与线性表的每个元素进行比较

查找的关键:比较
用平均比较次数来评估算法的优劣,平均查找长度ASL(Average Search Length)

 

2.折半查找算法,也叫二分查找算法

折半查找算法性能分析
-时间复杂度是log(2)n,效率高
-但必须是有序的
-只适用于顺序存储结构

 

3.分块查找(没记,大概是您翻ppt太快了)

 

4.哈希表查找

哈希表查找:构造哈希函数
(1)直接定值法:线性函数,没有冲突!
(2)模法(除留余数法) H(k) = k%m
可能有冲突,解决冲突:
(1)开放定址法:(线性探测、二次探测、伪随机探测)从发生冲突的那个单元格开始,按照一定的次序,从哈希表中找出一个空闲的存储单元,把发生冲突的待插入关键字存储到该单元中,从而解决冲突的发生。
(2)再哈希法:
(3)链地址法:将所有相互发生冲突的同义词(哈希地址相同的关键字)存储在同一个单链表中。若干组同义词可以组成若干个单链表,可用一维数组存放头指针。

哈希函数的构造目标是使哈希地址尽可能均匀地分布在散列空间上,同时使计算尽可能简单。

-冲突:两个不同的关键词有可能对应同一个内存地址,将导致后放的关键字无法存储,这种现象叫冲突;
-同义词:具有相同函数值的关键字称为同义词;


##1、直接定址法
构造:取关键字或关键字的某个线性函数作哈希地址

2、数字分析法
构造:对关键字进行分析,取尽量随机的若干位或其组合作哈希地址

3、平方取中法
构造:先计算构成关键字的平方,然后按照散列表的大小取中间的若干位作为散列地址

4、折叠法
构造:将关键字分割成位数相同的几部分,然后取这几部分的叠加和(舍去进位)作哈希地址

##5、除留余数法
构造:用关键字k除以不大于散列表长度的数m所得余数作为哈希地址,即有H(k) = k%m
特点:
~简单常用,可与上述的集中方法结合使用
~m的选取很重要;m选的不好,容易产生同义词
~较理想的m值,使得每一个关键字通过该函数转换后映射到散列空间上任一地址的概率都相等,从而尽可能减少发生冲突的可能性。一般情形下,m取为一个素数较理想,并且要求装填因子a最好是在0.6~0.9之间,所以m最好取1.1n~1.7n之间的一个素数较好,其中n为散列表中的元素个数。

 

 第四章 数据结构

集合:是一种聚集、组织了其他对象的对象
数据结构:逻辑结构、物理(存储)结构、数据运算。
逻辑结构:线性结构、非线性结构

线性:不分叉的、一条路走到黑的。(线性表、栈、队、串、数组)
a.线性表:(集合)由n个具有相同特性的数据元素组成的有限序列。用顺序结构存储。
   物理结构:(1)顺序存储结构,顺序表,ArrayList(2)链式存储结构,LinkedList。
   (一)创建:head = null
   (二)插入:头插法、尾插法 插入a6,头:a6->a2,head->a6;尾:p = head,找到尾(p->next! = null, p = p->next), p ->a6
   (三)查找:p = p.next
   (四)删除:查找(三), p->next.value = a1, p->next = p->next->next
   (五)修改:查找、赋值=
b.栈和队列:特殊的线性表
c.数组:顺序储存结构
d.链表:链式储存结构(单链表和双链表)
   -结点信息(data)、相邻结点地址(next),数据域、指针域/链域
   -头插法:s.next ->a.next 或者b.next ->a.next => s.next ->b.next
   -动态数据结构、指针占空间、非随机存取、插入删除方便
e.串:特殊的线性结构
非线性:树结构、图结构

物理(存储)结构:顺序、链式、索引、散列
数据运算:插入、删除、修改、查找、排序
数据结构:逻辑结构+物理结构+算法

 

第五章 栈

栈定义:特殊的线性表,先进后出/后进先出

【生活中的案例】
拉粑粑:先进先出;吃了吐:后进先出
【特殊】
·插入删除都在栈顶
·栈顶、栈底
·Top指向栈顶元素

插入:Push入栈
删除:Pop出栈

StackADT.java

public void push(T element);//入栈
public T pop();//出栈
public T peek(); //取栈顶的元素,只读取,不插入删除
public boolean isEmpty();//判断栈是否为空
public int size();//栈有多少个元素

【栈的应用】

~伪代码~
voidmultiBase(int N,int B){
int i;
Stack s = new Stack();
While(N){
Push (&S,N%B);
s.push(N%B);
N=N/B;
}
while(!s.empty(S)){
i=Pop(&S);
s.pop();
printf("%d",i);
}


【后缀式】
1.设立一个空栈(用于存放运算符);
2.从左到右扫描原表达式,遇到数据直接输出,并输出一个空格分隔不同数据;
3.遇到运算符,则与栈顶比较,级别高进栈,否则退出栈顶元素并输出。然后输出空格作分隔符;
4.遇到左括号进栈,遇到右括号一直退栈输出直到遇到左括号;
5.当栈为空则输出的结果为后缀表达式;

【后缀式求值步骤】
遇到运算符从栈中退出两个元素,先退出的房运算符右边,后退出的放运算符左边,运算后的结果再进栈直到后缀表达式扫描完毕。


数据结构一张图→集合→列表(数组ArrayList+链表LinkedList)

 

第六章 队列

队/队列queue:线性结构、先进先出、入队【插入(队尾)】、出队【删除(队头)】

enqueue-入队
dequeue-出队
first-
isEmpty-判断是否为空
size-长度
toString-输出队列

LinkedQueue<T> implements QueueADT<T>{
LinearNode<T> front;
LinearNode<T> rear;
int count;
}

front指向队头,rear指向队尾的下一个位置。
当front和rear指向同一个位置时候,队列为空。
入队列:q[rear++]=x;
出队列:e=q[front++];

public void enqueue(T element);
public boolean isEmpty();
public int siza();

 

public class QueueADT<T>{

}

 

public class LinkedQueue<T> implements QueueADT<T>{
private int count;
private LinearNode<T> head,tail;

public LinkedQueue(){
count = 0;
head = tail = null;
}

@override
public void enqueue(T element){
LinkedNode<T> node = new LinkedNode<T>(element);
if(isEmpty())
head = node;
else
tail.setNext()
tail = node;
count++;
}

@ovrride
public T dequeue() throws EmptyCollectionException{
if(isEmpty()){
throw new EmptyCollectionException("queue");
}

@ovrride
public String toString(){
String st = "";
LinearNode temp = head;
while (!temp.equals(taile)){
st = st + temp.getElement();
}
return st;
//或者: return "LinkedQueue{" + "name=" + name +"; number=" + number + "; hobby=" + bobby;
//此处输出的方法为引用的Student类里的方法(但是不美观)
}
}


LinkedQueueTest{
public static void main(String[] args){
LinkedQueue <Student> linkedQueue = new LinkedQueue<>();
linkedQueue.enqueue(new Student("小吉",20202302,打游戏);//为Student类里的方法
//可以重复上一行
System.out.println(linkedQueue);
}

 

第七章 排序

时间效率:排序的时间开销可用算法执行中的数据比较次数与数据移动次数来衡量
空间效率:占内存辅助空间的大小
稳定性:若两个记录A与B的关键字值相等,但排序后A、B的先后次序保持不变,则称这个排序算法是稳定的。

由排序元素的位置所在的不同可分为内部排序和外部排序。
内部排序:排序期间所有数据对象都放在内存里
外部排序:对象过多,不能同一时间在内存中进行排序,只能在内外存中来回移动

内部排序:插入排序、交换排序、选择排序、归并排序、基数排序、希尔排序、堆排序
简单排序:直接插入、折半排序、冒泡排序、简单选择排序

【插入排序】:
1、直接插入排序
直接插入排序的特点:元素逐步前移到合适位置,且在原数据基本有序的时候,需要移动数据最少。
时间复杂度:O(n^2)
2、对半插入排序/折半插入排序
3、2-路插入排序
4、插入排序之——希尔排序(缩小增量排序)(对直接插入排序的改进)
时间复杂度:目前未算出精确的渐进时间
【交换排序】:
1、冒泡排序:n个数据中每相邻一对进行比较,大了就交换,直到最大的数移到最后一位,再在n-1个数据中重复进行以上步骤。时间复杂度:O(n^2)
2、快速排序:(对冒泡排序的改进)任取序列中某个元素(一般选第一个)作为枢轴,将一组数据分为大、小两组,然后在每个组内继续下分为大、小两组,直到排序完毕。
怎么找枢轴:设i、j,从i=头部和j=尾部向中间靠,两数字进行比较,小的换前面,大的换后面,i++或者j++,直到i和j相遇,此时两个所对应的同一个值即为枢轴。
【选择排序】
(1)简单选择排序(不稳定排序)
1.从待排序序列中,找到关键字最小的元素;
2.如果最小元素不是待排序序列的第一个元素,将其和第一个元素互换;
3.从余下的 N - 1 个元素中,找出关键字最小的元素,重复(1)、(2)步,直到排序结束。
(2)堆排序
【归并排序】:2路归并排序
【基数排序】:从个、十、百等数位依次放入0~9个表,依照个位数大小开始排序,排好后的数列又开始依照十位数大小开始排序,直到依照最高位排序完成。

 

第八章 树

树定义:n(n≥1)个有限节点组成一个具有层次关系的集合。把它叫做“树”是因为它看起来像一棵倒挂的树,也就是说它是根朝上,而叶朝下的。
每个结点有零个或多个子结点;没有父结点的结点称为根结点;每一个非根结点有且只有一个父结点;除了根结点外,每个子结点可以分为多个不相交的子树。

 

(一)树操作

结点:
根结点:没有父结点的结点
结点的度:结点的子树数
树的度:结点的最大度数
叶子(leaf):度为0
分支点(branch):非终端结点
结点的层次(level):根为第一层,以此类推
树的深度(depth):结点的最大层次
有序树,无序树(我笔记写的有无序数......)
树和森林

1.查找操作
getboot() //返回根结点
isEmpty() //判断是否为空
depth()
traverse() //遍历树(每个元素只看一次)
2.插入操作
tree() //构造函数,初始化置空树
assign() //给当前结点赋值
insert() //插入操作,可以使结点或者子树
3.删除操作
makeEmpty() //将树清空
Delete() //删除结点或子树


(1)孩子表示法
(2)孩子父亲表示法
(3)孩子兄弟表示法

 

(二)二叉树
结点度数最多为2:至多两棵子树
有序树:子树有左右之分
二层树每层最多有2^(k-1)个结点
二叉树最多有2^k-1个结点
完全二叉树的高度为[log(2)n] +1

满二叉树:每一个结点上接一、下接二
完全二叉树(最下面一层把左边全填满,空只能空右边的)=满二叉树去掉最下层最右边的若干个结点

最浪费的情况就是只有一条链,而且全是左边或者全是右边。

(三)遍历
按某种搜索路径访问一个树的每个结点,而且每个结点仅被访问一次

访问VISIT:对结点的各种操作,如输出结点中的数据,修改结点中的数据等。

二叉树由根、左子树、右子树三部分组成,定义为D、L、R
D、L、R的组合定义了六种可能的遍历方案
DLR DRL
LDR RDL
LRD RLD

1.先序遍历算法框架:若二叉树为空则空操作;否则:
(1)访问根结点;
(2)先序遍历左子树;
(3)先序遍历右子树。

2.中序遍历算法框架                                      :
若二叉树为空,则空操作;否则:
(1)中序遍历左子树;
(2)访问根结点;
(3)中序遍历右子树。

3.后序遍历算法框架:
若二叉树为空,则空操作;否则:
(1)后序遍历左子树;
(2)后序遍历右子树;
(3)访问根结点。

作用:
打印出结点数据、修改结点中的数据、统计结点个数……


后序定根,中序分左右

已知先序和后序的时候不能确定二叉树呢,必须知道中序+先/后序才可以


(四)二叉树的层序遍历:
队列实现(如下)和数组实现

根结点入队;
从队头取元素
并执行如下三个动作
(1)访问该节点
(2)如果该元素有左孩子,则左孩子入队;
(3)如果该元素有右孩子,则右孩子入队;
重复执行上述过程,直至队列为空。
此时,二叉树遍历结束。

(五)二叉排序树
又称二叉搜索(查找)树
结构:左子树<根结点<右子树

若二叉排序树为空,则查找不成功。
(1)若给定值等于根结点的关键字,则查找成功
(2)若给定值小于根结点的关键字,则继续在左子树上进行查找
(3)若给定值大于等于根结点的关键字,则在右子树上进行查找
从根结点出发,沿着左分支或者右分支逐层向下直至关键字等于给定值的结点或者直至指针指向空树为止。

1.递归算法:
在根指针T所指二叉树中递归地查找某个关键字等于key的数据元素,若查找成功,则返回指向该数据元素的指针,否则返回空指针。
非递归算法:
在根指针T所指二叉树中查找某个关键字等于key的数据元素,若查找成功,则返回指向该数据元素的指针,否则返回空指针。

2.插入算法

3.删除算法
删除要在查找成功之后进行,并且在删除某个人结点之后,仍要保持二叉排序树的特性。
可分三种:
(1)被删除的结点是叶子:直接根结点指向null
(2)被删除的结点只有左子树或右子树:其双亲节点的相应指针域指向被删除的结点的左子树或右子树
(3)被删除的左子树右子树都有:用前驱或者后继替换掉该节点。前驱是该节点左子树的最右边的叶子(除了第一次是往左读,后面只能往右读),后继是该节点右子树的最左边的叶子(第一次往右读,后面只能往左读)


(六)二叉树的平衡化:
平衡二叉树的插入删除会破坏它的平衡性。
平衡二叉树:
·二叉树的每个结点的左右子树的深度之差的绝对值不超过1
·结点的左子树深度减去右子树深度的值,称为该节点的平衡因子(教材写的相反)
·平衡二叉树又称为AVL树
·红黑树

过长:指深度之差大于1
右旋:树根左孩子的左子树路径过长导致不平衡
左旋:树根右孩子的右子树路径过长导致不平衡
右左旋:树根右孩子的左子树过长导致不平衡
左右旋:树根左孩子的右子树过长导致不平衡

 

(七)哈夫曼树

最优二叉树/哈夫曼树:平均编码长度最短/带权路径长度最小的二叉树
路径长度:连接两结点的路径上的分枝数
树的带权路径长度:树中所有的叶子结点的带权路径长度之和
在哈夫曼树中,权值越大的结点离根越近
构造哈夫曼树:自低而上

 

第九章 堆

堆是一颗完全二叉树,每个结点小于或大于等于其左孩子和右孩子
如果一颗完全二叉树是堆,则根结点一定是最大值(或最小值)
堆用顺序结构存储最为合适
最小堆(小顶堆):
最大堆(大顶堆):
完全:n结点,h=log(2)n(下取整)+1,h,h-1

方法:
addElement
removeMin

插入:
插入与重排序

删除:
删除最小值,并重构堆
删除root,把最后一个叶子移动到根的位置
依次调整

选择排序之堆排序
筛选

非终端结点:
终端结点:

堆结构的建立

 

第十章 图

从回收站里找出来三个宝贝,哈夫曼树补到上面去了

 

 

 

 

 

(一)图的定义:图是线性表or树中结点间关系的扩展

无向图:图中任意两顶点之间的边都是无向边
有向图

稀疏图、稠密图

有很少条边或弧(如e<nlog(2)n),n是图的顶点数

邻接点:边的两个临点
关联边:e=(v,u)

边的权:图的边(或弧)带有与该边相关的数据信息
网络:边(或弧)上带权的图成为网

顶点的度、出度、入度
度=出度+入度

路径与回路
路径:从顶点v1出发,沿着一些边经过各个顶点到达顶点vn,则称顶点序列(v1,v2,......vn)为从v1到vn的一条路径
回路:若路径上第一个顶点v1与最后一个顶点vm重合,则称这样的路径为回路或环

连通图、非连通图
每一个顶点都不是孤立存在的

强连通图、弱连通图

连通分量:无向图G的一个极大连通子图称为G的一个连通分量(或连通分支)
生成树:包含无向图G所有顶点的极小连通子图称为G的生成树

图的存储方案
图的信息:顶点的数据、顶点间的关系
顶点信息:顶点值
边的信息:临接矩阵、邻接表、等


(二)【邻接矩阵】【邻接表】——特别重要
边集数组、十字链表——掌握即可

顶点:一维数组存放
边:二维数组存放

【邻接矩阵】
易判断两点间的关系,容易求得顶点的度,但占用空间大

无向图的邻接矩阵对称,可压缩存储
无向图中顶点vi的度是邻接矩阵中第i行1的个数
有向图的邻接矩阵不一定对称
有向图中顶点vi的出度是邻接矩阵中第i行1的个数,入度是第i列1的个数

邻接矩阵复杂度
1)时间复杂度:O(1)
2)空间复杂度:O(n^2)

【边集数组】
二维数组,对空间要求比较小,但不宜判断两点关系,也不宜计算结点的度。

【邻接表】
节省空间,易得到顶点的出度,但不易判断两点间的关系,不易得到顶点的入度

无向图:
若无向图中有n个结点、e条边,则其邻接表需要n个头结点和2e个表结点。诗意存储稀疏图
无向图中顶点vi的度为第i个单链表中的结点数

有向图:
顶点vi的出度为第i个单链表中的结点个数
顶点vi的入度为整个单链表中连接点阈值是i-1的结点个数
找出度容易,找入度难

【逆邻接表】
顶点vi的入度为第i个单链表中的结点个数
顶点vi的出度为整个单链表中连接点阈值是i-1的结点个数
找入度容易,找出度难

【十字链表】
【邻接多重表】
【存储结构归结比较】

广度优先遍历:水波

深度优先遍历:一条路走到黑

prim算法基本思想:对于图G而言,V是所有顶点的集合;现在,设置两个新的集合U和T,其中U用于存放G的最小生成树中的顶点,T存放G的最小生成树中的边。 从所有uЄU,vЄ(V-U) (V-U表示出去U的所有顶点)的边中选取权值最小的边(u, v),将顶点v加入集合U中,将边(u, v)加入集合T中,如此不断重复,直到U=V为止,最小生成树构造完毕,这时集合T中包含了最小生成树中的所有边。

kruskal算法基本思想:按照权值从小到大的顺序选择n-1条边,并保证这n-1条边不构成回路。首先构造一个只含n个顶点的森林,然后依权值从小到大从连通网中选择边加入到森林中,并使森林中不产生回路,直至森林变成一棵树为止。

Dijkstra算法基本思想:通过Dijkstra计算图G中的最短路径时,需要指定起点s(即从顶点s开始计算)。引进两个集合S和U。S的作用是记录已求出最短路径的顶点(以及相应的最短路径长度),而U则是记录还未求出最短路径的顶点(以及该顶点到起点s的距离)。初始时,S中只有起点s;U中是除s之外的顶点,并且U中顶点的路径是”起点s到该顶点的路径”。然后,从U中找出路径最短的顶点,并将其加入到S中;接着,更新U中的顶点和顶点对应的路径。 然后,再从U中找出路径最短的顶点,并将其加入到S中;接着,更新U中的顶点和顶点对应的路径。 … 重复该操作,直到遍历完所有顶点。

 

(三)拓扑排序:

1.在有向图中选一个没有直接前驱的顶点,并输出;
2.从途中删除该顶点和所有以它为尾的边
3.重复以上 1、2 步, 直到:
  全部顶点均已输出,形成了拓扑序列,或图中还有未输出的顶点,但已跳出循环。这说明图中还剩下一些顶点,它们都有直接前驱。说明该AOV网络中必定存在有向环。


拓扑序列结果不唯一;
可以获得拓扑序列的有向图中一定不存在环。


最长的路径是工程的最短时间
该最长路径长度的路径叫做关键路径,它的活动最早开始时间和最迟开始时间相等即l(i)-e(i)=0的路径

活动最早开始的时间:e(i)
从开始点v1到某点vi的最长路径长度叫做事件vi最早发生的时间ve(i)
活动最迟开始时间l(i):在不推迟整个工程完成时间的前提下,活动ai必须最迟开始进行的时间

 

 

二、总结所做过的作业

 

作业1:实验三 面向对象程序设计(1)

参考 http://www.cnblogs.com/rocedu/p/6371315.html#SECUNITTEST 
参考http://www.cnblogs.com/rocedu/p/6736847.html

提交最后三个测试用例都通过的截图,截图上要有画图加水印,输入自己的学号。

作业2:实验三 面向对象程序设计(2)

参考 积极主动敲代码,使用JUnit学习Java (http://www.cnblogs.com/rocedu/p/4837092.html)
参考http://www.cnblogs.com/rocedu/p/6736847.html
以 TDD的方式研究学习StringBuffer,提交你的单元测试用例和测试通过的截图,截图要加上学号水印。

作业3:实验三 面向对象程序设计(3)

实验三 Java面向对象程序设计(http://www.cnblogs.com/rocedu/p/4472842.html)

参考http://www.cnblogs.com/rocedu/p/6736847.html

对设计模式示例进行扩充,体会OCP原则和DIP原则的应用,初步理解设计模式
用自己的学号%6进行取余运算,根据结果进行代码扩充:
0:让系统支持Byte类,并在MyDoc类中添加测试代码表明添加正确,提交测试代码和运行结的截图,加上学号水印
1:让系统支持Short类,并在MyDoc类中添加测试代码表明添加正确,提交测试代码和运行结的截图,加上学号水印
2:让系统支持Boolean类,并在MyDoc类中添加测试代码表明添加正确,提交测试代码和运行结的截图,加上学号水印
3:让系统支持Long类,并在MyDoc类中添加测试代码表明添加正确,提交测试代码和运行结的截图,加上学号水印
4:让系统支持Float类,并在MyDoc类中添加测试代码表明添加正确,提交测试代码和运行结的截图,加上学号水印
5:让系统支持Double类,并在MyDoc类中添加测试代码表明添加正确,提交测试代码和运行结的截图,加上学号水印

作业4:实验三 面向对象程序设计(4)

提交:单元测试代码和运行成功截图及码云上代码链接,截图要加上学号水印

参考http://www.cnblogs.com/rocedu/p/6736847.html

任务:以TDD的方式开发一个复数类Complex,要求如下:

// 定义属性并生成getter,setter
double RealPart;
double ImagePart;

作业5:实验三 面向对象程序设计(5)

使用[WhiteStarUML](http://whitestaruml.sourceforge.net/)对实验二中的代码进行建模,发类图的截图,加上学号水印。
参考http://www.cnblogs.com/rocedu/p/6736847.html
类图中只少两个类。

作业6:封装继承多态重写重载文件字符字节读写

编写一组程序,要体现一下知识点:
(1)继承
(2)多态
(3)重写
(4)重载
(5)目录创建
(6)文件创建
(7)字节流读写
(8)字符流读写

本题16分,每个知识点2分。超时扣10分。
要求:每个知识一个程序。

 

作业7:实现自己的ArrayList

1.编写自己的ArrayList类
要求:实现增加、删除、修改、查找、判断是否为空、返回list长度等操作。
2.测试。

作业8:实验四(1):Java Socket编程

Java Socket编程(2分)
1.学习蓝墨云上教材《Java和Android编程》“第16章 输入/输出 ”和“第22章 网络”,学习JavaSocket编程
2.结对编程。结对伙伴A编写客户端SocketClient.java,结对伙伴B编写服务器端。
3.截图加学号水印上传蓝墨云,代码push到码云,并撰写实验报告。

作业9: 实验四(2):Java和密码学

参考 http://www.cnblogs.com/rocedu/p/6683948.html,以结对的方式完成Java密码学相关内容的学习(帖子中所有代码和相关知识点需要学习)。
提交学习成果码云链接和代表性成果截图,要有学号水印。

作业10:实验四 (3)编写有理数/复数计算器

结对编程,结对伙伴A编写有理数计算器。结对伙伴B编写复数计算器。(本题2分)
1.截图加水印上传蓝墨云,代码push码云
2.撰写实验报告

作业11:实验四 (4)远程有理数计算器

结对编程,结对伙伴A编程实现客户端,结果伙伴B实现服务器端。
客户端通过键盘输入一个有理数计算的公式(例如:1/4 + 1/6 = ),并把该公式以字符串的形式发送给伙伴B(服务器端),服务器端根据字符串计算出结果为5/12,并把结果返回给客户端A,A收到结果后输出结果。截图加水印上传蓝墨云,代码push码云。

作业12:实验四 (5)远程复数计算器

结对编程,结对伙伴B编程实现客户端,结果伙伴A实现服务器端。
客户端通过键盘输入一个有理数计算的公式(例如:1/4 + 1/6 = ),并把该公式以字符串的形式发送给伙伴A(服务器端),服务器端根据字符串计算出结果为5/12,并把结果返回给客户端B,B收到结果后输出结果。截图加水印上传蓝墨云,代码push码云。

作业13:ArrayStack测试

(1)撰写自己的类;
(2)提供StackADT,ArrayStack(框架),实现ArrayStack里面的剩余方法;
(3)编写测试类,测试所写的方法是否正确。

作业14:栈应用-进制转换

算法基于原理:     N = (N div d)×d + N mod d  
例如:(1348)10 = (2504)8 ,其运算过程如下:
        N        N div 8        N mod 8
     1348           168                 4
       168             21                 0
         21               2                 5
           2               0                 2

要求输入一个十进制数,转换成任意进制数并输出。

作业15:最小生成树测试

1.画出Prim算法的最小生成树的生成过程
2.画出Kruscal算法的最小生成树的生成过程
3.计算最小权值

作业16:最后一次测试


三、实验报告链接汇总

 (每个实验好像都没有一个总结的名称)

实验一 实验名称:简要内容

实验二 实验名称:简要内容

实验三 实验名称:简要内容

实验四 实验名称:简要内容

实验五六 实验名称:简要内容

实验七 实验名称:简要内容

实验八 实验名称:简要内容

实验九 实验名称:简要内容

 

四、代码托管链接

 

五、课程收获与不足

 

 怎么说,新学一门编程语言当然是很有用的。java与C语言有许多共同之处, 编程语言都有共同之处。最大的共同之处就是编程思想。 

投入的效率。。。。。。果然夜间是投入效率最高的时候。

最后悔的是idea没安装中文版的,每每遇到bug还需要查百度翻译。

 但是总的怎么说,就是idea用法还是不够清晰,java的很多用法还没有贯彻清楚牢固。

最后一句心里鸡汤:虽然数据结构课程结束了,但是学习数据结构的路永无止境。虽然我们课上学了java一门语言,但是学习其他编程语言的路也永无止境!

posted @ 2022-01-02 20:47  20202322袁艺匀  阅读(165)  评论(1)    收藏  举报