Comp 110 Style

Preview:

DESCRIPTION

Comp 110 Style. Instructor: Jason Carter. Interfaces and More Style. Define contracts between our users and implementers Optional – they may not be used Good style to use them Will study additional elements of style in this chapter. Two Ways of Doing the BMI Spreadsheet. - PowerPoint PPT Presentation

Citation preview

COMP 110STYLE

Instructor: Jason Carter

2

INTERFACES AND MORE STYLE Define contracts between our users and

implementers Optional – they may not be used Good style to use them Will study additional elements of style in this

chapter

3

TWO WAYS OF DOING THE BMI SPREADSHEET

ABMISpreadsheet is one way to implement the spreadsheet user-interface

Let us create AnotherBMISpreadsheet to illustrate another way

Difference is in number of variables used

4

BMI SPREADSHEET

5

ABMISPREADSHEETABMISpreadsheet Instance

weight height

getWeight()

setWeight()

getHeight()

setHeight() getBMI()

ObjectEditor

calls

writes

weight

calls

reads

height

calls

reads writes

callsnew

weight

new height

reads

6

ANOTHERBMISPREADSHEETAnotherBMISpreadsheet Instance

weight height

getWeight()

setWeight()

getHeight()

setHeight() getBMI()

ObjectEditor

calls

writes

weight

calls

reads

height

calls

readswrites

callsnew

weight

new height

reads

bmi

7

METHODS THAT CHANGEABMISpreadsheet Instance

weight height

setWeight()

setHeight() getBMI()

ObjectEditor

writes

calls

writes

callsnew

weight

new height

reads

bmi

8

SETWEIGHT()ABMISpreadsheet Instance

weight

setWeight()

ObjectEditor

writes

calls new

weight

bmi

public void setWeight(double newWeight) {

weight = newWeight;bmi = weight / (height*height);

}

9

SETHEIGHT()ABMISpreadsheet Instance

height

setHeight()

ObjectEditor

writes

calls new

height

bmi

public void setHeight(double newHeight) {

height = newHeight;bmi = weight / (height*height);

}

10

GETBMI()ABMISpreadsheet Instance

getBMI()

ObjectEditor

reads

bmi

public double getBMI() {return bmi;

}

11

COMPLETE CODEpublic class AnotherBMISpreadsheet { double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = weight/(height*height); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = weight/(height*height); } public double getBMI() { return bmi; }}

12

GRAPHICAL ALGORITHMABMISpreadsheet Instance

weight height

getWeight()

setWeight()

getHeight()

setHeight() getBMI()

ObjectEditor

calls

writes

weight

calls

reads

height

calls

readswrites

callsnew

weight

new height

reads

bmi

13

ENGLISH ALGORITHM Declare three instance variables

weight, height and, bmi Define three getter methods return values of the

three instance variables Define two setter methods to change weight and

height The setter methods assign new weight and

height values and compute and assign new BMI value to bmi

14

ALGORITHM Description of solution to a problem Can be in any “language”

graphical natural or programming language natural + programming language (pseudo code)

Can describe solution to various levels of detail

15

STEPWISE REFINEMENT

Declare three instance variables weight, height and, bmi

Define three getter methods return values of the three instance variables

Define two setter methods to change weight and height

The setter methods assign new weight and height values and compute and assign new BMI value to bmi

public void setWeight(double newWeight) {

weight = newWeight;bmi = weight/(height*height);

}

Natural Language

Programming Language

16

OBJECTEDITOR USER INTERFACE?public class AnotherBMISpreadsheet { double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = weight/(height*height); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = weight/(height*height); } public double getBMI() { return bmi; }}

17

OBJECTEDITOR USER INTERFACES

18

SIMILARITIES IN THE TWO CLASSESpublic class AnotherBMISpreadsheet { double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = weight/(height*height); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = weight/(height*height); } public double getBMI() { return bmi; }}

public class ABMISpreadsheet { double height; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; } double weight; public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

19

REAL-WORLD ANALOGY

manufactures

Corvette Specification

implements

implementsmanufactures

20

INTERFACE

21

public class AnotherBMISpreadsheet implements BMISpreadsheet { double height, weight, bmi; public double getHeight() { return height; } public void setHeight (double newHeight) { height = newHeight; bmi = weight/(height*height); } …

IMPLEMENTING AN INTERFACE Contract

Parameter names never

matter to Java

22

implements

implements

INTERFACE

ABMISpreadsheet

BMISpreadsheetABMISpreadsheet

instance

ABMISpreadsheetinstance

instance of

AnotherBMISpreadsheet

AnotherBMISpreadsheetinstance

AnotherBMISpreadsheetinstance

instance of

23

implements

implements

USING INTERFACES TO CLASSIFY

ABMISpreadsheet

BMISpreadsheetBMISpreadsheet

instance

BMISpreadsheetinstance

instance of

AnotherBMISpreadsheet

BMISpreadsheetinstance

BMISpreadsheetinstance

instance of

24

USING CAR SPECIFICATIONS TO CLASSIFY

manufactures

Corvette Specification

implements

implementsmanufactures

Corvette

Corvette

Corvette

Corvette

25

CANNOT INSTANTIATE SPECIFICATION Cannot order a car from a specification

Must order from factory A car defined by Corvette specification ordered from

factory implementing the specification

Cannot instantiate interface Must instantiate class BMISpreadsheet instance created by instantiating

class implementing interface

26

INTERFACE AS A SYNTACTIC SPECIFICATIONpublic class ABMISpreadsheet implements

BMISpreadsheet{ double height; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; } double weight; public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

27

INTERFACE AS A SYNTACTIC SPECIFICATIONpublic class ABMISpreadsheet implements

BMISpreadsheet{ double height; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; } double weight; public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return 13450; }}

Syntactic Contract

Bombay Market Index

28

INTERFACE REQUIRED Define interfaces for

All classes (that are instantiated) Some are not Include all public methods

29

DIFFERENCES IN THE TWO CLASSESpublic class AnotherBMISpreadsheet { double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = weight/(height*height); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = weight/(height*height); } public double getBMI() { return bmi; }}

public class ABMISpreadsheet { double height; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; } double weight; public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

30

ABMISPREADSHEET VS. ANOTHERBMISPREADSHEET

ABMISpreadsheet uses less space (variables) Getter methods of AnotherBMISpreadhseet are

faster Setter methods of ABMISpreadsheet are faster Usually getter methods are called more often

that setter methods e.g. when ObjectEditor refresh command is

executed Typically AnotherBMISpreadsheet will be faster,

overall

31

TIME-SPACE TRADEOFF

Time MiserSpace Miser

Space

Time

32

TIME-SPACE TRADEOFF

Space

Time

Time MiserSpace Miser

33

RELATING INTERFACE AND CLASS NAMESClass Name:

<Qualifier><Interface> - ABMISpreadsheet- ASpaceEfficientBMISpreadsheet- SpaceEfficientBMISpreadsheet

<Interface><Qualifier> Impl- BMISpreadsheetImpl- BMISpreadsheetSpaceEfficientImpl

Interface Name:

<ClassName>Interface- ABMISpreadsheetInterface

34

PROGRAMMING STYLE: THE ART OF PROGRAMMING

Science of programming Does the program work correctly?

Art programming Does the program follow “good” style rules?

Good style rules make it easier to Get the program working correctly Change the program

35

WRITING STYLE To the point Avoid repetition Good flow Illustrate ideasThere is more than one way to write a document

that conveys some facts: e.g. the influence of BMI on health

36

PROGRAMMING STYLE: THE ART OF PROGRAMMING

Define interfaces Make programs

efficient Space vs. time

Comment program Use appropriate

identifier names Use named constants

Variables vs. names Constants vs. magic

numbers

Avoid code repetition Give least privilege

No public instance variables

Implementation independent constants in interfaces

Initialize variables Independent code in

separate method

There is more than one way to write a program that correctly meets its specification: e.g.

implement the BMI user-interface

37

PROGRAMMING STYLE: THE ART OF PROGRAMMING

Use Interfaces

Efficiency

Comment Program

Avoid Code Repetition

Giving Least Privilege

Use Named Constants

38

COMMENTS

double bmi; //computed by setWeight and setHeight

Single line comments

/* This version recalculates the bmi when weight or height change, not when getBMI is called*/public class AnotherBMISpreadsheet {…}

/* recompute dependent properties */bmi = weight / (height * height);

Arbitrary comments

39

JAVADOC CONVENTIONS

/* This version recalculates the bmi when weight or height change, not when getBMI is called*/public class AnotherBMISpreadsheet {…}

/* This version recalculates the bmi* when weight or height change, not when* getBMI is called*/public class AnotherBMISpreadsheet {…}

You should use this convention

40

System.out.println(newHeight); /*debugging statement */

REMOVING DEBUGGING CODE

/* System.out.println(newHeight); /*debugging

statement */ */

/* System.out.println(newHeight); // debugging

statement */

41

WHAT TO COMMENT? Any code fragment needing explanation

ClassTop-level algorithm, author, date modified

Variable declarationPurpose, where used, how its value is computed

Method declarationparams, return value, algorithm, author, date modified

Statement sequenceExplanation

Debugging codeSummarizing vs. Elaborating Comments?

42

WHAT TO COMMENT?

double w; // weight

double weight; // weight

double weight;

double bmi; // computed by setWeight and setHeight

Bad variable name

Redundant

Self-commenting

Useful comment

43

JAVADOC TAGS

/* * @author Prasun Dewan * @param newWeight the new value of the property, weight. * sets new values of the variables, weight and bmi */public void setWeight (double newWeight) {

…}

/* * @author Prasun Dewan * @return the value of the variable, weight */public double getWeight () {

…}

JavaDoc tags

44

COMMENTING INTERFACES

/* * @param newWeight the new value of the property, weight */public void setWeight (double newWeight) { }

/* * @return the value of the variable, weight */public double getWeight () { }

Implementation independent comments

Commenting both interface and implementation?

45

PROGRAMMING STYLE: THE ART OF PROGRAMMING

Use Interfaces

Efficiency

Comment Program

Avoid Code Repetition

Giving Least Privilege

Use Named Constants

46

IMPROVING THE STYLEpublic class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = weight/(height*height); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = weight/(height*height); } public double getBMI() { return bmi; }}

Code repetition

Assuming ABMICalculator does not exist

47

IMPROVING THE STYLE (EDIT)public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } … public void setWeight(double newWeight) { weight = newWeight; bmi = calculateBMI(); } public double getBMI() { return bmi; }

double calculateBMI() { return weight/(height*height); }}

48

RE-USING CODEpublic class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = calculateBMI(); } double calculateBMI() { return weight/(height*height); } ….}

49

CHANGING RE-USED CODE ONCEpublic class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = calculateBMI(); }

double calculateBMI() { return (weight/2.2)/(height * 2.54/100*height*2.54/100); } …}

Declaring vs. calling methods?

50

PROGRAMMING STYLE: THE ART OF PROGRAMMING

Use Interfaces

Efficiency

Comment Program

Avoid Code Repetition

Giving Least Privilege

Use Named Constants

51

ONLY PUBLIC METHODS IN INTERFACE

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } … double calculateBMI() () { return (weight/2.2)/(height * 2.54/100*height*2.54/100); } …}

Not in interface

52

PRINCIPLE OF LEAST PRIVILEGE Do not give a user of some code more rights

than it needs Code is easier to change Need to learn less to use code Less likelihood of accidental or malicious damage to

program Like hiding engine details from car driver

ObjectEditor

ABMICalculator User ABMICalculator

getWeight() setWeight()

getHeight() setHeight()

getBMI() computeBMI()

53

IMPROVING THE STYLE

Use Interfaces

Efficiency

Comment Program

Use Named Constants

Avoid Code Repetition

Giving Least Privilege

54

IMPROVING THE STYLE

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } … double calculateBMI() () { return (weight/2.2)/(height * 2.54/100*height*2.54/100); } …}

Magic numbers

55

IMPROVING THE STYLE

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } … double calculateBMI() () { return (weight/LBS_IN_KG) / (height*CMS_IN_INCH/100*height*CMS_IN_INCH/100); } …}

Named constants

56

DECLARING NAMED CONSTANTS

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; ... final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() { return (weight/LBS_IN_KG) / (height*CMS_IN_INCH/100*height*CMS_IN_INCH/100); } …}

Un-initializing declarationInitializing declaration

57

MORE ON VARIABLES VS. NAMED CONSTANTS

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; ... double lbsInKg = 2.2; double cmsInInch = 2.54; … double calculateBMI() { return (weight/lbsInKg) / (height*cmsInInch/100*height*cmsInInch/100); } …}

58

ACCIDENTAL OR MALICIOUS MODIFICATION

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; ... double lbsInKg = 2.2; double cmsInInch = 2.54; … double calculateBMI() { lbsInKg = 22; return (weight/lbsInKg) / (height*cmsInInch/100*height*cmsInInch/100); } …}

Violating least privilege

59

LITERALS VS. NAMED CONSTANTS VS. VARIABLES

Use constants for program values that do not change Use named constants for magic numbers

60

MORE CODE REPETITION

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; ... final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() { return (weight/LBS_IN_KG) / (height*CMS_IN_INCH/100*height*CMS_IN_INCH/100); } …}

Within same method and has the same value

61

REMOVING CODE REPETITION (EDIT)

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; ... final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() { double heightInMeters = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMeters*heightInMeters); } …}

62

REMOVING CODE REPETITION

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; ... final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() { double heightInMeters = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMeters*heightInMeters); } …}

63

LOCAL VS. GLOBAL VARIABLE

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; double heightInMeters = height*CMS_IN_INCH/100; ... final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() { return (weight/LBS_IN_KG) / (heightInMeters*heightInMeters); } …}

64

LOCAL VS. GLOBAL VARIABLEpublic class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; double heightInMeters = height*CMS_IN_INCH/100; ... final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … public void setHeight(double newHeight) { heightInMeters = newHeight; bmi = calculateBMI(); } … double calculateBMI() { return (weight/LBS_IN_KG) / (heightInMeters*heightInMeters); } …}

Violating least privilege

65

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = weight/(height*height); } … double calculateBMI () { double heightInMetres = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

SCOPE

heightInMeters scope

Not a scope

height scope

66

SCOPE OF PUBLIC ITEMS

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … public double getWeight() { return weight; } …}

ObjectEditor

ABMISpreadsheet

getWeight() scope

67

IDENTIFIER SCOPE Region of code where the identifier is visible Arbitrary scopes not possible Least Privilege => Make scope as small as

possible

68

SCOPEpublic class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … public void setHeight(double newHeight) { height = newHeight; bmi = calculateBMI(); } public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; bmi = weight/(height*height); } … double calculateBMI() () { double heightInMetres = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

heightInMeters scope

69

INITIALIZING DECLARATION

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() () { double heightInMetres = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

70

UN-INITIALIZING DECLARATION

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() () { double heightInMetres; heightInMeters = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

71

UN-INITIALIZED VARIABLE

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() () { double heightInMetres; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

72

INITIALIZING ALL VARIABLES

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height, weight, bmi; … final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() () { double heightInMetres; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

73

INITIALIZING ALL VARIABLES (EDIT)

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height = 60, weight = 70, bmi = getBMI(); … final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() () { double heightInMetres = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

74

INITIALIZING ALL VARIABLES

public class AnotherBMISpreadsheet implements BMISpreadsheet{ double height = 70, weight = 160, bmi = calculateBMI(); … final double LBS_IN_KG = 2.2; final double CMS_IN_INCH = 2.54; … double calculateBMI() () { double heightInMetres = height*CMS_IN_INCH/100; return (weight/LBS_IN_KG) / (heightInMetres*heightInMetres); } …}

75

PRINTING PROPERTIESpublic class ABMISpreadsheet implements BMISpreadsheet { double height; public double getHeight() { return height; } public void setHeight(double newHeight) { height = newHeight; } double weight; public double getWeight() { return weight; } public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

76

PRINTING PROPERTIES (EDIT)

public class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { System.out.println(“Height: “ + newHeight); height = newHeight; } double weight; … public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

77

PRINTING PROPERTIESpublic class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); double bmi = getBMI(); System.out.println(“BMI: “ + bmi); height = newHeight; } double weight; … public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

78

LESS CLUTTERED CODE (EDIT)public class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); double bmi = getBMI(); System.out.println(“BMI: “ + bmi); height = newHeight; } double weight; … public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

79

LESS CLUTTERED CODEpublic class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); System.out.println(“BMI: “ + getBMI()); height = newHeight; } double weight; … public void setWeight(double newWeight) { weight = newWeight; } public double getBMI() { return weight/(height*height); }}

80

REMOVING DUPLICATIONpublic class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); System.out.println(“BMI: “ + getBMI()); height = newHeight; } double weight; … public void setWeight(double newWeight) { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); System.out.println(“BMI: “ + getBMI()); weight = newWeight; } public double getBMI() { return weight/(height*height); }}

81

REMOVING DUPLICATION (EDIT)public class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { printProperties();height = newHeight; } double weight; … public void setWeight(double newWeight) { printProperties();weight = newWeight; } public double getBMI() { return weight/(height*height); } void printProperties() { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); System.out.println(“BMI: “ + getBMI()); }}

82

REMOVING DUPLICATIONpublic class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { printProperties(); height = newHeight; } double weight; … public void setWeight(double newWeight) { printProperties(); weight = newWeight; } … void printProperties() { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); System.out.println(“BMI: “ + getBMI()); }}

83

SEPARATION OF CONCERNSpublic class ABMISpreadsheet implements BMISpreadsheet { double height; … public void setHeight(double newHeight) { printProperties(); height = newHeight; } double weight; … public void setWeight(double newWeight) { printProperties(); weight = newWeight; } … void printProperties() { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); System.out.println(“BMI: “ + getBMI()); }}

Less cluttered

84

INDEPENDENT CODE = METHOD Separate method for:

Any independent piece of code Even if it is not duplicated If it is more than one line

public void setWeight(double newWeight) { System.out.println(“Weight: “ + weight); weight = newWeight;}

public void setWeight(double newWeight) { printWeight(); weight = newWeight;}

85

PRINTING BMI IN GETBMI()

public class ABMISpreadsheet implements BMISpreadsheet { double height; … public double getBMI() { printProperties(); return weight/(height*height); } … void printProperties() { System.out.println(“Weight: “ + weight); System.out.println(“Height: “ + height); System.out.println(“BMI: “ + getBMI()); }}

getBMI() never terminates

Recursive, calls itself indirectly

Infinite recursion

Avoid recursion for now

86

NON-PUBLIC INSTANCE VARIABLES

public class ABMISpreadsheet implements BMISpreadsheet { double height, weight, bmi; …}

87

MAKING INSTANCE VARIABLES PUBLIC

public class ABMISpreadsheet implements BMISpreadsheet { public double height, weight, bmi; …}

Other classes

88

HARD TO CHANGE

public class ABMISpreadsheet implements BMISpreadsheet { public double height, weight; …}

Other classes

89

CONSISTENCY CONSTRAINTS VIOLATED

Inconsistent values

90

PRECONDITIONS CANNOT BE ENFORCED

More on this later

91

ENCAPSULATION PRINCIPLE Do not make instance variables public

Expose them through public methods

92

public final double CMS_IN_INCH = 2.54;

PUBLIC CONSTANTS

public interface BMISpreadsheet {

public final double CMS_IN_INCH = 2.54;

}

Inconsistent value cannot be stored

Implementation independent ABMISpreadsheet

AnotherBMISpreadsheet

93

PRINCIPLE Declare implementation-independent named

constants in interfaces implementing classes can access them

94

95

EXTRA SLIDES

96

STEPWISE REFINEMENT

Declare two instance variables weight and height

Define a getter method that computes the value of BMI and returns it

public double getBMI() {return weight/(height*height);

}

Natural Language

Programming Language

97

REAL-WORLD ANALOGY

manufactures

Corvette Specification

implements

implementsmanufactures