Testing, Debugging, and Verification | TDA567/DIT082, LP2, HT2017 |
Lab 1 - Software Testing | |
This lab is divided into three parts:
The programming language of the assignments is Java. When deriving test cases you are supposed to use JUnit to organise and run your test cases.
Installation instruction for JUnit: here. 1. Black-box TestingThe assignment is about a class called WorkSchedule. The purpose of the class is to manage the schedule for the employees of a company. The time is divided in units of 1 hour and the hours are simply identified by integers (Note that this is an unrealistic simplification). For each hour, the schedule stores the number employees which is needed at that time. It could for instance be that during week-days the need is that 5 employees work at the same time, but less during nights and weekend. For each hour the schedule also stores the names of the employees who have been assigned to work at that hour. The constructor and methods of the class are: public WorkSchedule(int size) { ... }
creates a schedule which contains the hours 0,1,2,...,size - 1 where for each hour the number of needed employees is set to zero and there are no employees assigned to it public Hour readSchedule(int time) { ... }
gives back an object of the class Hour, which has two fields: public void setRequiredNumber(int nemployee, int starttime, int endtime) { ... } sets the number of required working employees to nemployee for all hours in the interval starttime to endtime. public boolean addWorkingPeriod(String employee, int starttime, int endtime) { ... } schedules employee to work during the hours from starttime to endtime. public String[] workingEmployees(int starttime, int endtime) { ... } returns a list of all employees working at some point during the interval starttime to endtime. public int nextIncomplete(int currenttime) { ... } returns the closest time starting from currenttime for which the required amount of employees has not yet been scheduled. The constructor (WorkSchedule) and the methods readSchedule, setRequiredNumber, nextIncomplete, are trusted to be correct and do not need to be tested. Note that readSchedule can be used to examine the state of a class instance.
A compiled implementation of the class can be found in the following Java archive: Your task: For each specification provided below (i.e. specification for the methods addWorkingPeriod, and workingEmployees):
a) addWorkingPeriod
requires: employee is a non-null string ensures: if starttime < 0 or endtime >= size or starttime > endtime then returns false and the schedule is unchanged otherwise if for any hour in the interval starttime to endtime the length of workingEmployees is equal to requiredNumber then returns false and the schedule is unchanged otherwise if for any hour in the interval starttime to endtime there is a string in workingEmployees which equal employee then returns false and the schedule is unchanged otherwise returns true, for i between starttime and endtime, workingEmployees contain a string equal to employee and the rest of the schedule is unchanged
b) workingEmployees
requires: starttime >= 0 and endtime < size ensures: if starttime <= endtime then returns an array with distinct strings -- a string appears in the return array if and only if it appears in the workingEmployees of at least one hour in the interval starttime to endtime otherwise returns an empty array and in either case the schedule is unchanged
Reporting test cases
In a report file, you must explain and motivate why you divided the test cases in the way you did. You must show how you defined the input space, and how you partitioned it. Example: Given the method: public String m(int x);With the specification: requires: x != 0 ensures: if x > 0 then the method returns the String "High" otherwise the method returns the String "Low"Your report should read something like: Input space: x != 0 (or: "x" in { MIN_INT, ..., -1, 1, ..., MAX_INT } ) Partition #1: x > 0 (or: "x" in { 1, ..., MAX_INT } ) test_m_part1: input: "x = 155", expected: "m(x) = "High"" Partition #2: x < 0 (or: "x" in { MIN_INT, ..., -1 } ) test_m_part2: input: "x = -18", expected: "m(x) = "Low"" Border cases: test_m_border1: input: "x = MIN_INT", expected: "m(x) = "Low"" test_m_border2: input: "x = -1", expected: "m(x) = "Low"" test_m_border3: input: "x = 1", expected: "m(x) = "High"" test_m_border4: input: "x = MAX_INT", expected: "m(x) = "High"" Found bugs: None.
2. White-box TestingFor the assignments in part 2 you will be using the source code of the methods. For each method you should first derive a suite of test cases which together have full statement coverage of the source code. Then you should write additional test cases (if any are needed) which together with the ones already there have full branch coverage of the code. The test cases should be executable with JUnit just like in part 1 of the lab. If any of the test cases for a method fails, try to find the bug and correct the source code. Keep in mind that you may need a method, A, to set up the test of another method, B. If the method A has a bug it can be very tricky to test method B. Wherever possible you can first fix the bug in a method and then do the tests that use it in the setup (or test oracle). Also keep in mind that a bug in the implementation may imply that full statement or branch coverage is not possible. This it in itself an indication of the bug's existence. In such case, it's enough if you have full coverage after fixing the bug. The assignment is about the class Set.
> Set
Set represents sets of integers. The elements of a set are stored in an ArrayList. They are sorted and without duplicates to speed up some operations. Two methods might need an explanation: public void section(Set s) { ... } removes from this set any element that is equal to an element in s. public boolean containsArithTriple() { ... } returns true iff there are three elements, x, y and z, in this set such that y - x = z - y. Note that you can use toArray to easily examine the state of a class instance. a) Use statement and branch coverage to derive test cases for insert. b) Use statement and branch coverage to derive test cases for member. c) Use statement and branch coverage to derive test cases for section. d) Use statement and branch coverage to derive test cases for containsArithTriple. e) If you find any bugs, try to correct them in the implementation. Also keep in mind that it might be your specification that is incorrect. Make a new version of Set.java which passes all your tests.
3. DebuggingWhen an array is sorted, finding an element in that array becomes possible in logarithmic time by performing a binary search. The class BinarySearch implements a binary search for arrays of integers. However, there is a bug in the implementation of the method search. In the method main, replace the value 4 in the variable value by any other of the elements in array, and search will not be able to find it. Your task is to debug the previous implementation in order to find the error in method search. In your report for this exercise you must include a description of how you have debugged the previous method (e.g. break points used, etc).
Reporting
Upload an archive LAB1.zip (or rar, tar.gz, tar as you wish) using the Fire report system.
The archive must have the following structure: LAB1.zip | |-ex1 | |- <your_1st_test_class>.java | |- ... | |- <your_nth_test_class>.java | |- WorkScheduleTestSuite.java | \- report.txt | |-ex2 | |- <your_1st_Set_test_class>.java | |- ... | |- <your_mth_Set_test_class>.java | |- SetTestSuite.java | |- Set.java | \- report.txt | \-ex3 |- BinarySearch.java \- report.txt
| |
Home | Course | Schedule | Exam | Exercises | Labs | Evaluation | Tools | Srinivas Pinisetty, Nov 7, 2017 |