OO第二单元的作业主题是模拟电梯。

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

第一次作业:FAFS傻瓜调度-单电梯模拟

1、多线程的协同和同步控制

本次作业的线程只有两个:调度器线程和电梯线程。调度器线程负责接收指令并维护一个请求队列,请求队列使用单例模式构造,由于电梯采用傻瓜调度,因此电梯线程每次从调度器的请求队列中取一个指令执行。在本次作业中,调度器线程和电梯线程唯一需要共享的对象是请求队列,因此为了保证线程安全,应在请求队列的getqueue方法前加上synchronize关键字。

2、程序结构

本次作业有4个类:Main类、Elevator类、Dispatcher类、InputHandler类。类图如下:

类复杂度分析如下:

方法复杂度分析如下:

3、自己程序的bug

由于本次作业比较简单,我们首次接触多线程可能会出现有线程提前结束或无法结束的情况,这可能是在写代码的时候遇到的最大的困难,逻辑上的问题其实并没有多少,可以把这次的作业抽象为一个简单的生产者-消费者问题。公测和互测均未发现bug。

4、如何发现别人的bug

本次作业比较简单,因此发现别人的bug也不容易,我没有发现别人有逻辑上的bug。至于线程方面的bug,我有听说有些程序可能输入数据后过一段时间再输入ctrl+D会出现无法结束的情况,但我本人并没有发现这样的bug。测试策略方面,与第一单元的策略略有不同的是,我可以选择在不同的时间投放测试数据,或是在同一时间投放几个数据,以测试线程的运行是否正确。

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

第二次作业:ALS捎带调度-单电梯模拟

1、多线程的协同和同步控制

本次作业仍然是单电梯的调度,因此线程和第一次作业一样有两个:调度器线程和电梯线程。调度器线程的职责没变:负责接收指令并维护一个单例模式的请求队列。本次电梯的调度策略采用ALS捎带算法,电梯需要有一个主请求和若干个捎带请求,因此电梯需要自己维护一个请求队列。在本次作业中,调度器线程和电梯线程需要共享的对象还是调度器的请求队列,因此在调度器的getqueue方法前加上synchronize关键字。

2、程序结构

本次作业的类相比上一次并没有什么改变,还是4个类:Main类、Elevator类、Dispatcher类、InputHandler类。类图如下:

类复杂度分析如下:

方法复杂度分析如下:

3、程序bug

本次作业我完全采用了指导书中描述的ALS算法,因此正确性方面没有出问题,但同时性能分也基本没有。

4、如何发现别人的bug

与我同组的同学也基本采用同样的ALS算法,因此也很难找出逻辑上的漏洞。我没有发现bug。测试策略与本单元第一次作业基本相同,会加入一些可以捎带的请求组合来测试捎带算法的正确性与线程安全。

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

第三次作业:SS智能调度-多电梯模拟

1、多线程的协同和同步控制

本次作业是多电梯的调度,一共有三部电梯,因此是一个调度器线程和三个电梯线程并行。每部电梯能到达的楼层和运行速度均不同,乘客的请求可能无法由一部电梯直接送达,需要换乘,换乘的请求需要注意必须等到第一次电梯把乘客运送到换乘楼层之后第二部电梯才能接上乘客继续运送,注意到这点的情况下,我采用了电梯在运送完换乘的乘客后再将乘客放回请求队列并修改其属性信息,以保证正确的时间的先后顺序逻辑。本次电梯的调度策略并没有规定,我仍然采用ALS捎带算法。在本次作业中,调度器的请求队列可能被三部电梯同时访问而产生线程安全问题,因此我在每一个电梯上/下人的过程中都锁住了dispatcher这个对象以防止出问题。

2、程序结构

这次作业比上一次作业在捎带算法方面没有什么区别,只是多了需要换乘的乘客,因此我多了一个TransferPersonRequest类来处理需要换乘的请求,总共有5个类:Main类、Elevator类、Dispatcher类、InputHandler类、TransferPersonRequest类。类图如下:

类复杂度分析如下:

方法复杂度分析如下:

3、程序bug

这次的bug很多,强测正确率8/20,错误主要是因为在处理有关3层的调度的时候出现了很严重的逻辑错误,导致有关3楼的需要换乘的请求基本都无法正确执行,互测也被人抓着这个bug无限hack。这也是因为我的换乘请求处理不够全面,从上面的复杂度分析也可以看出,我的代码中有些方法复杂度太高,难以看出错误。

4、如何发现别人的bug

本次作业,有关3楼的换乘请求的处理确实是一个难点,因此我首先就用关于3楼的请求来测试其他同学,如1-FROM-3-TO-4,2-FROM-2-TO-3等,结果和我的情况差不多,互测的同学也基本在处理3层的请求时出现了问题,可能会出现乘客在3楼无限循环出入电梯的情况。其他的问题由于有了前两次作业的基础,并没有发现很多。

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

心得体会

这三次作业都是有关多线程的。多线程程序中最重要的一点就是保证线程安全,我这三次作业基本没有出现线程安全的问题,这是很好的一点。关于线程安全需要注意的地方总结一下就是:某个共享资源(对象)在同时被多个线程访问并进行读写操作时可能会出现线程安全的问题,为了避免线程安全问题,可以采用在访问共享对象的时加锁、尽量不要将自己对象的修改权随便交给其他对象、在外部对象想要访问自己对象中的元素时,返回该元素的一个副本而不是该元素本身等方法。在设计原则方面,最好是每个对象做好自己的事,尽量减少与其他对象的交互,即所谓的“解耦”,这样既更加符合面向对象的思想,也可能可以减少锁的使用,提高多线程并行的效率。此外需要特别提出的一点就是,在这三次作业中,中测出现次数很多的问题是CPU_TIME_LIMIT_EXCEED,即CPU时间过长,这往往是由于程序中存在轮询的情况而导致的,比如在调度器请求队列中没有请求时,电梯可能会无限循环去检测请求队列中有没有请求,这样电梯线程就会一直占用着CPU资源,导致CPU时间超时。解决的办法也很简单,只需要利用sleep()或是wait()和notifyAll(),在电梯检测到调度器请求队列为空的时候让电梯线程等待一段时间或是等待直到被唤醒即可。

2019OO第二单元作业总结的更多相关文章

  1. 【BUAA-OO】第二单元作业总结

    第二单元作业总结 ——电梯恐惧症患者的极限自救 一.   第一次作业程序分析 1.     设计策略简略分析 线程:主线程.输入线程和电梯线程,另有一个持有请求队列的调度器,一个对输入进行处理的Req ...

  2. OO第二单元作业总结【自我反思与审视】

    第二单元作业的完成史,就是一部心酸的血泪史…… 多线程的出现为我(们)打开一片广阔的天地,我也在这方天地摸爬滚打,不断成长!如果说第一单元之前还对Java语法有所了解的话,那么这单元学习多线程则完全是 ...

  3. BUAA_OO第二单元作业总结——多线程

    OO第二单元作业总结——多线程 单元任务 本单元主要的内容是通过模拟电梯的运行来熟悉多线程的实现,从简单的单部FAFS电梯开始,ALS电梯,到最后的多部ALS电梯. 一.设计策略分析总结 1.1 多线 ...

  4. 【OO学习】OO第二单元作业总结

    OO第二单元作业总结 在第二单元作业中,我们通过多线程的手段实现了电梯调度,前两次作业是单电梯调度,第三次作业是多电梯调度.这个单元中的性能分要求是完成所有请求的时间最短,因此在简单实现电梯调度的基础 ...

  5. BUAA OO 2019 第二单元作业总结

    目录 总 架构 controller model view 优化算法 Look 算法 多种算法取优 预测未来 多线程 第五次作业 第六次作业 第七次作业 代码静态分析 UML 类图 类复杂度 类总代码 ...

  6. 电梯也能无为而治——oo第二单元作业总结

    oo第二单元作业总结 一.设计策略与质量分析 第一次作业 设计策略 在第一次作业之前,我首先确定了生产者--消费者模式的大体架构,即由输入线程(可与主线程合并)充当生产者,电梯线程充当消费者,二者不直 ...

  7. OO第二单元作业小结

    前言 转眼已是第九周,第二单元的电梯系列作业已经结束,终于体验了一番多线程电梯之旅. 第一次作业是单电梯的傻瓜调度,虽然是第一次写多线程,但在课程PPT的指引下,写起来还是非常容易:第二次作业是单电梯 ...

  8. 电梯模拟系统——BUAA OO第二单元作业总结

    需求分析 官方需求 本次作业需要模拟一个多线程实时多电梯系统,从标准输入中输入请求信息,程序进行接收和处理,模拟电梯运行,将必要的运行信息通过输出接口进行输出. 本次作业电梯系统具有的功能为:上下行, ...

  9. 我永远爱着OOP——第二单元作业总结

    第二单元的电梯真是愉♂快呢,多线程编程作为java编程OOP中的重要组成部分,通过这一个单元的学习,我也是有了很多全新的认识 那么下面就先例行一下公事 三次作业分析 第五次作业 设计分析 实现的电梯是 ...

随机推荐

  1. 总结AWS使用要点

    最近做毕业设计,要用AWS跑代码,以前只用过一次,这次踩了很多坑,记录一下.. AWS命令行管理S3 bucket AWS官方文档: http://docs.amazonaws.cn/cli/late ...

  2. CodeForce-955C

    C. Sad powerstime limit per test2 secondsmemory limit per test256 megabytesinputstandard inputoutput ...

  3. Linux中一个文件10行内容,如何输出5-8内容到屏幕

    题目是这样的,Linux中一个文件10行内容,如何输出5-8内容到屏幕首先我们模拟一下这样的环境: [root@localhost question]# pwd /root/question [roo ...

  4. 【转载】DQL、DML、DDL、DCL的概念与区别

    原文地址:https://www.cnblogs.com/fan-yuan/p/7879353.html SQL(Structure Query Language)语言是数据库的核心语言. SQL的发 ...

  5. 【webpack学习笔记】a03-管理输出

    webpack 中输出管理主要运用了两个插件: html-webpack-plugin clean-webpack-plugin 这两个插件可以满足常规的输出管理需求. html-webpack-pl ...

  6. AStar算法()

    把网上的AStar算法的论述自己实现了一遍,一开始只是最基础的实现.当然,现在AStar算法已经演变出了各种优化的版本,这篇也会基于各种优化不断的更新. 如果对算法不熟悉可以看下Stanford的这篇 ...

  7. MySQL 必知必会学习笔记(常用命令二)

    CREATE TABLE students(student_id INT UNSIGNED, name VARCHAR(30), sex CHAR(1), birth DATE, PRIMARY KE ...

  8. python模块和包(模块、包、发布模块)

    模块和包 目标 模块 包 发布模块 01. 模块 1.1 模块的概念 模块是 Python 程序架构的一个核心概念 每一个以扩展名 py 结尾的 Python 源代码文件都是一个 模块 模块名 同样也 ...

  9. 使用IdentityServer4,在一个ASPNetCore项目中,配置oidc和api的AccessToken两种认证授权

    1.配置两种认证方式 JwtSecurityTokenHandler.DefaultInboundClaimTypeMap.Clear(); services.AddAuthentication(op ...

  10. elasticsearch(5) 请求体搜索

    上一篇提到的轻量搜索非常简单便捷,但是通过请求体查询可以更充分的利用查询的强大功能.因为_search api中大部分参数是通过HTTP请求体而非查询字符串来传递的. 一 空查询 对于空查询来说,最简 ...