copyright © 2014 by john wiley & sons. all rights reserved.1 chapter 8 – designing classes

63
Copyright © 2014 by John Wiley & Sons. All rights reserved. 1 Chapter 8 – Designing Classes

Upload: robert-holmes

Post on 26-Dec-2015

217 views

Category:

Documents


1 download

TRANSCRIPT

Page 1: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 1

Chapter 8 – Designing Classes

Page 2: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 2

Chapter Goals

To learn how to choose appropriate classes for a given problem

To understand the concept of cohesion To minimize dependencies and side effects To learn how to find a data representation for a class To understand static methods and variables To learn about packages

Page 3: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 3

Discovering Classes A class represents a single concept from the problem

domain.

Name for a class should be a noun that describes concept. • Concepts from mathematics:

PointRectangleEllipse

• Concepts from real life: BankAccountCashRegister

Page 4: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 4

Discovering Classes Actors

• objects do some kinds of work for you:ScannerRandom // Better name: RandomNumberGenerator

Utility classes • no objects, only static methods and constants:

Math

Program starters: • a class with only a main method

Page 5: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 5

Naming Classes

The class name should indicate what objects of the class will do:

• Paycheck is a better name than PaycheckProgram.

Don't turn a single operation action into a class:

• Paycheck is a better name than ComputePaycheck.

Page 6: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 6

Question

Answer: Look for nouns in the problem description.

What is the rule of thumb for finding classes?

Page 7: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 7

Designing Good Methods - Cohesion

A class should represent a single concept.

The public interface of a class is cohesive if all of its features are related to the concept that the class represents.

The members of a cohesive team have a common goal.

Page 8: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 8

Designing Good Methods - Cohesion

This class lacks cohesion.

public class CashRegister{ public static final double QUARTER_VALUE = 0.25; public static final double DIME_VALUE = 0.1; public static final double NICKEL_VALUE = 0.05; . . . public void receivePayment(int dollars, int quarters, int dimes, int nickels, int pennies) . . .}

It contains two concepts:• A cash register that holds coins and computes their total• The values of individual coins.

Page 9: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 9

Designing Good Methods - Cohesion

Solution: Make two classes:

public class Coin{

double value;String type;

public Coin(double aValue, String aName) { . . . } public double getValue() { . . . } . . . } public class CashRegister{ . . . public void receivePayment(int coinCount, Coin coinType) { payment = payment + coinCount * coinType.getValue(); } . . . }

Now CashRegister class can handle any type of coin.

Page 10: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 10

Minimizing Dependencies A class depends on another class if its methods use

that class in any way.

• CashRegister depends on Coin

UML: Unified Modeling Language

• Notation for object-oriented analysis and design

Page 11: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 11

Minimizing Dependencies

Figure 1 UML class diagram showing dependency relationship between the CashRegister and Coin Classes.

The Coin class does not depend on the CashRegister class.

Page 12: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 12

Separating Accessors and Mutators A mutator method:

• changes the state of an object (i.e. modify value of instance variables).• E.g. withdraw method in BankAccount class

An accessor method:• asks an object to compute a result• doesn’t change the state (i.e. only looks up value of instance variable).• E.g. getBalance method in BankAccount class

An immutable class:• Class with no mutator methods.• E.g. String is an immutable class

• No method in the String class can modify the contents of a string.

• References to objects of an immutable class can be safely shared.

A mutable class:• accessors + mutators

Page 13: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 13

Separating Accessors and Mutators

Mutator method:• Change the state of an object• Usually a method that does NOT return a value.• In general, SHOULD have return type void• Sometimes, can return an informational value.

• E.g. ArrayList remove method returns true if the removal was successful.

Page 14: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 14

Minimizing Side Effects In general, a method should not modify its parameter

variables./** Computes the total balance of the given accounts. @param accounts a list of bank accounts*/public double getTotalBalance(ArrayList<BankAccount> accounts){ double sum = 0; while (accounts.size() > 0) { BankAccount account = accounts.remove(0); // Not recommended sum = sum + account.getBalance(); } return sum;}

Such a side effect would not be what most programmers expect.

Page 15: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 15

Programming Question Add following method below main moethod of BankAccountTester class.

public double getTotalBalance(ArrayList<BankAccount> accounts) { double sum = 0; while (accounts.size() > 0) { BankAccount account = accounts.remove(0); // Not recommended sum = sum + account.getBalance(); } return sum; }

Modify main method by creating array list accounts and adding 3 bank account objects with balance $1000, $2000 and $3000 respectively. Print the balances of each account object balance.

Next call getTotalBalance method with accounts as argument

Print balances of each account object in acconts arrayList again.

Page 16: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 16

Answerimport java.util.ArrayList;

public class BankAccountTester{ public static void main(String args[]) { ArrayList<BankAccount> accounts = new ArrayList<BankAccount>(); BankAccount acct1 = new BankAccount(1000.00); accounts.add(acct1); BankAccount acct2 = new BankAccount(2000.00); accounts.add(acct2); BankAccount acct3 = new BankAccount(3000.00); accounts.add(acct3);

for(BankAccount acct: accounts)System.out.print("BankAccount balance before:"+ acct.getBalance());

System.out.println();

getTotalBalance(accounts);

for(BankAccount acct: accounts)System.out.print("BankAccount balance after:"+ acct.getBalance());

System.out.println(); } public static double getTotalBalance(ArrayList<BankAccount> accounts) { double sum = 0; while (accounts.size() > 0) { BankAccount account = accounts.remove(0); // Not recommended sum = sum + account.getBalance(); } return sum; }}

BankAccountTester.java

Page 17: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 17

Output:

Page 18: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 18

Minimizing Side Effects The following method mutates the System.out

object, which is not a part of the BankAccount object.

public void printBalance() // Not recommended{ System.out.println("The balance is now $" + balance);}

That is a side effect.

Lesson learned:• When designing methods, minimize side effects.• Keep most of your classes free from input and output

operations

Page 19: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 19

Question

Is the Rectangle class immutable?

Page 20: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 20

Answer

Answer: No – translate is a mutator.

Is the Rectangle class immutable?

Page 21: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 21

static Variables and Methods - Variables A static variable:

• Also called class variables• Belongs to the class, not to any object of the class.

• E.g. To assign bank account numbers sequentially • Have a single value of lastAssignedNumber that is a property of

the class, not any object of the class.• Declare it using the static reserved word

public class BankAccount{ private double balance; private int accountNumber; private static int lastAssignedNumber = 0; public BankAccount(double balance) {

this.balance = balance; lastAssignedNumber++; accountNumber = lastAssignedNumber; } . . .}

Page 22: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 22

Programming Question

Modify BankAccount class to incorporate an accountNumber variable (and lastAssignedNumber ). Implement a toString method that returns a string with the String representation of class(E.g. “Bank Account No:1 balance:1000.0”).

Modify BankAccountTester class to create multiple bank accounts with different balances and print the details of each bank account using toString method.

A sample run is shown:

Page 23: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 23

Answer

public class BankAccount{ private double balance; private int accountNumber; private static int lastAssignedNumber = 0; public BankAccount(double balance) { this.balance = balance; lastAssignedNumber++; accountNumber = lastAssignedNumber; } public String toString() { return "Bank Account No:"+accountNumber+" balance:"+balance; }}

BankAccount.javapublic class BankAccountTester{ public static void main(String args[]) { BankAccount acct1 = new BankAccount(1000.00); BankAccount acct2 = new BankAccount(2000.00); BankAccount acct3 = new BankAccount(3000.00); System.out.println(acct1); System.out.println(acct2); System.out.println(acct3); }}

BankAccountTester.java

Page 24: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 24

static Variables and Methods Every BankAccount object has its own balance and

accountNumber instance variables

All objects share a single copy of the lastAssignedNumber variable (static/class variable)

• That variable is stored in a separate location, outside any BankAccount objects

Page 25: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 25

static Variables and Methods

Figure 5 A static Variable and Instance Variables

Page 26: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 26

static Variables and Methods static variables:

• Should always be declared as private, • This ensures that methods of other classes do not change their

values

static constants:• May be either private or public

public class BankAccount{ public static final double OVERDRAFT_FEE = 29.95; . . .}

• Methods from any class can refer to the constant as

BankAccount.OVERDRAFT_FEE

Page 27: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 27

static Variables and Methods - Methods Sometimes a class defines methods that are not

invoked on an object

• Called a static method

Example: sqrt method of Math class

• a static method

• invoked as Math.sqrt(x)

• No object of the Math class is constructed.

Page 28: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 28

static Variables and Methods You can define your own static methods:

public class Financial{ /** Computes a percentage of an amount. @param percentage the percentage to apply @param amount the amount to which the percentage is applied @return the requested percentage of the amount */ public static double percentOf(double percentage, double amount) { return (percentage / 100) * amount; }}

Page 29: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 29

static Variables and Methods When calling such a method, supply the name of the

class containing it:

double tax = Financial.percentOf(taxRate, total);

The main method is always static.

• When the program starts, there aren’t any objects.

• Therefore, the first method of a program MUST be a static method.

Programming Tip:

• Minimize the Use of static Methods

Page 30: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 30

Question

Answer: System.in and System.out.

Name two static variables of the System class.

Page 31: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 31

Question

Answer: Math.PI

Name a static constant of the Math class.

Page 32: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 32

Question

Answer: The method needs no data of any object. The only required input is the values argument.

The following method computes the average of an array of numbers:public static double average(double[] values)

Why should it not be defined as an instance method?

Page 33: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 33

Question

Answer: Yes, it works. static methods can access static variables of the same class. But it is a terrible idea. As your programming tasks get more complex, you will want to use objects and classes to organize your programs.

Harry tells you that he has found a great way to avoid those pesky objects: Put all code into a single class and declare all methods and variables static. Then main can call the other static methods, and all of them can access the static variables. Will Harry's plan work? Is it a good idea?

Page 34: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 34

Packages

Package: Set of related classes Important packages in the Java library:

/opt/java-jdk/src.zip

Page 35: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 35

Organizing Related Classes into Packages

In Java, related classes are grouped into packages.

Page 36: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 36

Organizing Related Classes into Packages

To put classes in a package, you must place a line

package packageName;

as the first instruction in the source file containing the classes.

Package name

• consists of one or more identifiers separated by periods.

• Usually all lower case

Page 37: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 37

To put the Financial class into a package named com.horstmann.bigjava, the Financial.java file must start as follows:

package com.horstmann.bigjava;

public class Financial

{

. . .

}

Page 38: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 38

Organizing Related Classes into Packages

A special package: default package

• Has no name

• No package statement

• If you did not include any package statement at the top of your source file

o its classes are placed in the default package.

Page 39: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 39

Package Names Use packages to avoid name clashes:

java.util.Timer

vs.

javax.swing.Timer

Package names should be unique.

A good choice for package name:

• turn the domain name in reverse:

com.horstmann.bigjava

• Or write your email address backwards:

edu.sjsu.cs.walters

Page 40: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 40

Syntax 8.1 Package Specification

Page 41: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 41

Packages and Source Files

The path of a class file must match its package name.

The parts of the name between periods represent successively nested directories.

Base directory:

• holds your program's files

• Place the subdirectory inside the base directory.

• If your homework assignment is in a directory

/home/britney/hw8/problem1

Place the class files for the com.horstmann.bigjava package into the directory:

o /home/britney/hw8/problem1/com/horstmann/bigjava (UNIX)

o Or c:\Users\Britney\hw8\problem1\com\horstmann\bigjava (Windows)

Page 42: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 42

Packages and Source Files

Figure 6 Base Directories and Subdirectories for Packages

Page 43: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 43

Programming Question

Create a package cs160:1. Modify both BankAccount.java and CashRegister.java to

include the package statement: package cs160;2. Copy their main method bodies in corresponding Tester

classes as the last method in classes.Download classes from class website.

3. Compile these two files and copy the two .class files generated into a subdirectory called cs160.

cs160

BankAccount.javaBankAccount.classCashRegister.javaCashRegister.class

You will find that for successful compilation you need to manually create cs160 folder and put source (java) files there.

Once compiled, source files are not required

Page 44: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 44

Test if it works:• From current directory (shell prompt) $ java cs160.BankAccount$ java cs160.CashRegister

Page 45: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 45

Alternative way to create packages (easier and recommended):1. Create/modify your java files in any location you want.

E.g. BankAccount.java

2. Go to shell prompt/command line and navigate (cd) to folder with source files

Page 46: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 46

3. Type javac command to compile each source fileE.g javac -d . BankAccount.java

This will automatically create the directory structure and place .class file in ch8 directory.

BankAccount.java

some directory

cs160

ch8

BankAccount.class

Page 47: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 47

Answerpackage cs160;import java.util.ArrayList;

public class BankAccount{ private double balance; private int accountNumber; private static int lastAssignedNumber = 0;

public BankAccount(double balance) { this.balance = balance; lastAssignedNumber++; accountNumber = lastAssignedNumber; } private double getBalance() { return balance; } public String toString() { return "Bank Account No:"+accountNumber+" balance:"+balance; } public static void main(String args[]) { ArrayList<BankAccount> accounts = new ArrayList<BankAccount>(); BankAccount acct1 = new BankAccount(1000.00); accounts.add(acct1); BankAccount acct2 = new BankAccount(2000.00); accounts.add(acct2); BankAccount acct3 = new BankAccount(3000.00); accounts.add(acct3); for(BankAccount acct: accounts) System.out.print("BankAccount balance before:"+ acct.getBalance()); System.out.println(); }}

BankAccount.java

Page 48: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 48

package cs160;public class CashRegister{ public static final double QUARTER_VALUE = 0.25 ,DIME_VALUE = 0.1, NICKEL_VALUE = 0.05, PENNY_VALUE = 0.01; private double purchase, payment; public CashRegister() { purchase = 0; payment = 0; } public void recordPurchase(double amount){ purchase = purchase + amount; }

public void receivePayment(int dollars, int quarters,int dimes, int nickels, int pennies) { payment = dollars + quarters * QUARTER_VALUE + dimes * DIME_VALUE + nickels * NICKEL_VALUE + pennies * PENNY_VALUE; }

public double giveChange(){ double change = payment - purchase; purchase = 0; payment = 0; return change; } public static void main(String[] args){ CashRegister register = new CashRegister(); register.recordPurchase(0.75); register.recordPurchase(1.50); register.receivePayment(2, 0, 5, 0, 0); System.out.print("Change: "); System.out.println(register.giveChange()); System.out.println("Expected: 0.25");

}}

CashRegister.java

Page 49: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 49

Add package to jar file list1. Create the jar file

• In the shell prompt (in parent directory of cs160/ch8) typejar cvf cs160.jar cs160/ch8/*.class

2. Add jar to classpath in DrJava:• EditPreferencesResourceLocationsExtraClassPathAddselect cs160.jar ok

Page 50: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 50

Importing Packages

Can use a class without importing: refer to it by its full name (package name plus class name):

java.util.Scanner in = new java.util.Scanner(System.in);

• Inconvenient

import directive lets you refer to a class of a package by its class name, without the package prefix:

import java.util.Scanner;

• Now you can refer to the class as Scanner without the package prefix.

• E.g. Scanner in = new Scanner(System.in);

Page 51: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 51

Importing Packages Can import all classes in a package:

import java.util.*;

Never need to import java.lang.

You don't need to import other classes in the same package .

Page 52: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 52

Programming Question

Import packages:• Write a tester class called PackageImportDemo which will test

importing packages (save this class in a completely different location than the location you have source/.class files for cs160 package you created)

• Import the package you created and test BankAccount class by creating a BankAccount object with balance $1000 and printing the balance by calling toString() method:

Page 53: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 53

Answer

import cs160.ch8.BankAccount;

public class PackageImportDemo{ public static void main(String args[]) { BankAccount acct = new BankAccount(1000.0); System.out.println(acct); }}

PackageImportDemo.java

Page 54: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 54

Unit Test Framework Compilers cannot check for logical errors:

• whether the results of a program or method are correct.

So how do you check those errors?• Developers need to test their programs to ensure that they

behave as expected. • (+) Sometimes it is simple:

• calling a method in the Interactions Pane to view its results

• (-) Developer should know expected answers.

A better solution: • Give the tests the answers you expect, and let the tests

themselves do all the work.

Page 55: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 55

Unit testing makes this quite easy.

Unit testing is the testing of single entity (class or method)

Fast Automation:• runs test cases significantly faster than human resources.

You write many small tests that create your objects and assert that they behave the way you expect in different situations.

A unit test framework known as JUnit (http://www.junit.org) automates the process of running these tests, letting you quickly see whether your program returns the results you expect.

Page 56: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 56

JUnit JUnit: http://junit.org

• A unit testing framework for the Java Programming Language

• Idea: "first testing then coding“

• Open source framework used for writing & running tests.

• Unit tests can be run automatically and they check their own results and provide immediate feedback.

• Shows test progress in a bar that is green if test is going fine and it turns red when a test fails.

• Built into some IDEs like BlueJ ,Eclipse and DrJava

• DrJava Junit documentation:

• http://www.drjava.org/docs/user/ch07.html

Page 57: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 57

JUnit

Philosophy:

• Whenever you implement a class, also make a companion test class.

• Run all tests whenever you change your code.

Page 58: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 58

JUnit

In DrJava:1. Write a JUnit test class 2. Test Current junit test case Document:

• Choose the "Test Current Document" command from the Tools menu to run the tests and view the results. 

Test all open junit test case documents :• Click the "Test" button on the toolbar or choo "Test All Documents"

from the Tools menu

Output:• Shown in the Test Output tab• Each test method turn green if it completes successfully and

red if it fails. • A progress bar will keep you updated on how many tests have

been run.

Page 59: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 59

JUnit

Unit tests are any public classes that extend the junit.framework.TestCase class

Have any number of methods with names beginning with the word "test“

Page 60: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 60

JUnit

Writing a Test Case:

Choose the "New JUnit Test Case" command from the File menu

This automatically generate a template with these conventions.

At the top of the file, include:• import junit.framework.TestCase;

The main class of the file must:• be public• extend TestCase

Page 61: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 61

JUnit Methods of this class to be run automatically when the

Test command is invoked must:• be public and not static• return void• take no arguments• have a name beginning with "test“

Test methods in this class can call any of the following methods (among others):• void assertTrue (String, boolean)

• issues an error report with the given string if the boolean is false.

• void assertEquals (String, int, int)• issues an error report with the given string if the two integers are

not equal. The first int is the expected value, and the second int is the actual (tested) value.

• void fail (String)• which immediately causes the test to fail, issuing an error report

with the given string.

Page 62: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 62

Simple Test Example

Simple Test Example Suppose you are writing a Calculator class that can

perform simple operations on pairs of integers.

First write testcase class with few tests for it Then write the Calculator class Compile both classes Run the tests to see if they pass

• “Tools Test current document”

Page 63: Copyright © 2014 by John Wiley & Sons. All rights reserved.1 Chapter 8 – Designing Classes

Copyright © 2014 by John Wiley & Sons. All rights reserved. 63

import junit.framework.TestCase;

public class CalculatorTest extends TestCase { public void testAddition() { Calculator calc = new Calculator(); // 3 + 4 = 7 int expected = 7; int actual = calc.add(3, 4); assertEquals("adding 3 and 4", expected, actual); }

public void testDivision() { Calculator calc = new Calculator(); // Divide by zero shouldn't work try

{ calc.divide(2, 0); fail("Should have thrown an exception!"); } catch (ArithmeticException e) { // Good, that's what we expect } }

}

public class Calculator{ public int add(int a, int b) { return a+b; } public int divide(int a, int b) { return a/b; }}

CaclulatorTest.java Caclulator.java