# Introdu tion to Problem Solving and Programming

through C++

Abhiram Ranade

Do not distribute

Abhiram Ranade, 2011

Contents

Prefa
e . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11

1 Introdu
tion

1.1

1.2

1.3

1.4

1.5

1.6

1.7

1.8

A simple program . . . . . . . . . . .

1.1.1 Exe
uting the program . . . .

Remarks . . . . . . . . . . . . . . . .

1.2.1 Exe
ution order . . . . . . . .

Repeating a blo
k of
ommands . . .

1.3.1 Drawing any regular polygon

1.3.2 Repeat within a repeat . . . .

Some useful turtle
ommands . . . .

Numeri
al fun
tions . . . . . . . . . .

Con
luding Remarks . . . . . . . . .

Overview of the book . . . . . . . . .

1.7.1 A note regarding the exer
ises

Exer
ises . . . . . . . . . . . . . . . .

2 A bird's eye view

2.1

2.2

2.3

2.4

2.5

2.6

2.7

2.8

2.9

2.10

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

**Representing real life entities using numbers
**

Representing numbers on a
omputer . . . .

2.2.1 Organization of a
omputer . . . . .

Memory . . . . . . . . . . . . . . . . . . . .

2.3.1 Storing text . . . . . . . . . . . . . .

2.3.2 Storing natural numbers . . . . . . .

2.3.3 Storing integers . . . . . . . . . . . .

2.3.4 Storing real numbers . . . . . . . . .

2.3.5 Remarks . . . . . . . . . . . . . . . .

Arithmeti
Logi
Unit . . . . . . . . . . . .

Input-Output Devi
es . . . . . . . . . . . . .

The
ontrol unit . . . . . . . . . . . . . . . .

2.6.1 Control Flow . . . . . . . . . . . . .

2.6.2 Some tri
ky instru
tions . . . . . . .

High level programming languages . . . . . .

Boot Loader . . . . . . . . . . . . . . . . . .

Con
luding Remarks . . . . . . . . . . . . .

Exer
ises . . . . . . . . . . . . . . . . . . . .

1

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

14

15

16

17

17

18

18

20

20

20

22

23

24

24

26

27

28

29

29

30

31

31

31

32

33

34

34

37

38

38

40

40

41

2

Abhiram Ranade, 2011. Do not distribute

3 Numbers

**3.1 Variables and data types . . . . . . . . . .
**

3.1.1 Remarks on Table 3.1 . . . . . . .

3.1.2 Types
har and bool . . . . . . . .

3.1.3 Identi

ers . . . . . . . . . . . . . .

3.1.4 Initializing variables . . . . . . . .

3.1.5
onst keyword . . . . . . . . . . .

3.1.6 Reading data into a variable . . . .

3.1.7 Printing . . . . . . . . . . . . . . .

3.1.8 Exa
t representational parameters .

3.2 Arithmeti
and assignment . . . . . . . . .

3.2.1 Modulo operator: % . . . . . . . . .

3.2.2 Subtleties . . . . . . . . . . . . . .

3.2.3 Expli
it type
onversion . . . . . .

3.2.4 Assignment expression . . . . . . .

3.3 Examples . . . . . . . . . . . . . . . . . .

3.4 Assignment with repeat . . . . . . . . . .

3.4.1 Programming Patterns . . . . . . .

3.4.2 In
rement and de
rement operators

3.4.3 Compound assignment operators .

3.5 Comments . . . . . . . . . . . . . . . . . .

3.6 Data invariants . . . . . . . . . . . . . . .

3.7 Con
luding remarks . . . . . . . . . . . . .

3.8 Exer
ises . . . . . . . . . . . . . . . . . . .

4 Simple pp graphi s

4.1

4.2

4.3

4.4

4.5

4.6

4.7

4.8

4.9

..........

Multiple Turtles . . . . . . . .

Other shapes besides turtles .

Commands allowed on shapes

4.4.1 Resetting a shape . . .

Cli
king on the
anvas . . . .

Proje
tile Motion . . . . . . .

Best

t straight line . . . . . .

Con
luding Remarks . . . . .

Exer
ises . . . . . . . . . . . .

initCanvas

5 Conditional Exe ution

5.1

5.2

5.3

5.4

5.5

5.6

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

The If statement . . . . . . . . .

Blo
ks . . . . . . . . . . . . . . .

Other forms of the if statement .

A dierent turtle
ontroller . . . .

5.4.1 \Buttons" on the
anvas .

The swit
h statement . . . . . .

Logi
al Data . . . . . . . . . . . .

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

42

42

44

44

45

45

46

47

47

48

48

50

50

51

52

52

53

54

56

57

57

58

59

60

62

62

62

63

64

65

65

65

66

67

67

69

69

71

72

73

74

75

77

3

Abhiram Ranade, 2011. Do not distribute

**5.6.1 Reasoning about logi
al data . . . . . . . . . . . . . . . . . . . . . . 78
**

5.6.2 Determining whether a number is prime . . . . . . . . . . . . . . . . 78

5.7 Exer
ises . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 80

6 Loops

**6.1 The while statement . . . . . . . . . . . . . . . .
**

6.1.1 Counting the number of digits . . . . . . .

6.2 Developing loop based programs . . . . . . . . . .

6.2.1 Hema
handra numbers . . . . . . . . . . .

6.2.2 Mark averaging . . . . . . . . . . . . . . .

6.3 The break statement . . . . . . . . . . . . . . . .

6.4 The
ontinue statement . . . . . . . . . . . . . .

6.5 The do while statement . . . . . . . . . . . . . .

6.6 The for statement . . . . . . . . . . . . . . . . .

6.6.1 Use of the
ontrol variable outside the for

6.6.2 Break and
ontinue . . . . . . . . . . . .

6.6.3 Style issue . . . . . . . . . . . . . . . . . .

6.6.4 Primality . . . . . . . . . . . . . . . . . .

6.6.5 Natural log by numeri
al integration . . .

6.6.6 Mark Averaging . . . . . . . . . . . . . . .

7 Computing ommon mathemati al fun tions

7.1 Taylor series . . . . . . . . . . . . .

7.1.1 Sine of an angle . . . . . . .

7.1.2 Natural log . . . . . . . . .

7.1.3 Some general remarks . . .

7.2 Bise
tion method for

nding roots .

7.3 Newton Raphson Method . . . . .

7.4 Greatest Common Divisor . . . . .

7.4.1 Proof of termination . . . .

7.4.2 Proof of
orre
tness . . . . .

7.5 Summary . . . . . . . . . . . . . .

7.5.1 Mathemati
al ideas . . . . .

7.5.2 Programming ideas . . . . .

8 Testing and Debugging

8.1

8.2

8.3

8.4

8.5

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

.

Clarity of spe i

. .3 End of . . . . . . . 8. . . 8. . . . . . . . . . Program Design . . . . Hand exe ute the program . . . . 8. . .5. . . . . .1 On the use of variables . . . . . . . . . . . . .2. . . . . . . . . Assertions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8. . .1 Input and output examples . . . . . .5. Testing . . . .1. . . . . .2 File I/O . . . . .1 Automated testing: input/output redire tion . . . . . . . . . . . . ation . . . . . . .5. . . 8. . .

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 83 83 85 86 86 88 91 92 92 93 94 95 95 95 96 97 100 100 101 102 103 103 105 107 108 108 109 109 110 112 112 114 114 115 115 116 117 118 118 119 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .le and reading errors . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

8 8. . 4 Abhiram Ranade.5.9 8. Do not distribute 8. . 8.7 8.5 Assert with .6 8.5.4 Input-Output expressions . 2011.

. . . . . . . . . . . . . . . . . . . .6 9. . Exer ises . . . . . . . . . . .4 9. . . . . . . . . . . . . . . .3 9. . . Debugging . . . . . . .1 9. . . . .1 randuv ommand in simple pp Con luding remarks . . . . . . 9 Fun tions 9. . .7 De. . . . . . . . . . .2 9. . . . .5 9. . . . .7. . . . . . . Random numbers . . . . . . .le reading . . 8. . .

. . . . . . . . . . . . . . . .1. . 9. . .1 Fun tion spe i. . . 9. Nested fun tion alls: LCM . .1 Exe ution: all by value .ning a fun tion . . . . . . . . . . . The ontra t view of fun tion exe ution . . . . . .3. . . . .

. . . . . . A text drawing program . . . . . . . . . . ation . . . . . . . . . . . . . . . . The main program is a fun tion! . . . . . Fun tions that do not return values . Organizing fun tions into . . . . . . .

. . .1 Fun tion De laration . . . . 9.7. 9.7. . . . . .7. . . . .3 Header . . .les . . .2 Separate ompilation and obje t modules . . . 9.

. . . .7. 10. . . .1.5 Forward de laration . . . . . . . . .2. . .8 Fun tion size and readability . . .1 Exe ution of re ursive g d . . . . . . . . . . . . . . .2 Re ursive pi tures . . 10. . . . 10 Re ursive Fun tions 10. . . .2 Interpretation of re ursive programs . . . . . . 10. .3 Corre tness of re ursive programs . . . . . . . . . . . . . . . . . . . . 10. . . 9. .4 Pa kaging software .1 Eu lid's algorithm for GCD . . .1 Hilbert spa e . . 9. . . . . . 9.7.1. . . . .les . . . . . . . . . 9.9 Con luding remarks . . . . . 10. .1. . .

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1 Using a loop . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 120 120 121 121 122 122 123 124 124 126 127 128 129 130 131 133 133 133 134 136 136 137 137 138 139 140 141 141 142 143 145 146 148 148 149 151 151 154 154 155 157 157 158 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .3. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .lling urve . . . . . . . . . . . . . . . . . . . . . . . . .1 Remarks . . . . . . . . . . . . . . . . . . . 11. . . . . . . . . . . . . . . . . . . . . . . . . . . .2. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .2 Histori al Remarks . . . . . . . . . . . . . . 11. . . . . . . . .3 Pointers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .4 The game of Nim . . . . . 10. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .3. . . . . . . . . . . .2 Referen e variables 11. . . . . . . . . . . . . . . . . . . . . 10. . . . . . . . 10. . . . . . . . . . . . . .2 Call by referen e . . . . . . . . . . . . . . . . . . . . . . . . . . . . .3 Hema handra numbers . . .2. . . . . . . . . . . . . . . . . . .4. . . . . . . . . . . . . . . . .1 Remarks . 10. . . . . . . . . . 10. . . . . . 11. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11 More on Fun tions 11. . . . . . . . . . . . . . . . . . . . . . . . .1 Some diÆ ulties . . . . . . . . . . . . . . . . . . . .5 Con luding remarks . . . . . . . .

5 Referen e vs.3. .6 11. .8 11. . 11.3. . . . Pointers .4 Use in fun tions . Fun tion Pointers . . 11. .4. . 11.3.3 Dereferen ing operator * 11.7 11. 2011.2 Pointer variables .4 11. . .1 Some simpli. 5 Abhiram Ranade. .3.1 \Address of" operator & 11. .3.5 11. Do not distribute 11. .

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .3. . . . . . . . . . . . . . . . .2. . . . . . . . . . . . . 12. . . . . . . . . . . . . . . . . . . 13. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .3. . . . .7 Representing Polynomials . . . . . . . . . . . . . . . . . . . . . . . . . . . 12. . .1 Chara ter strings . . . . . . . . . . . . 13 More on arrays 13. . . . . . . . . . . . . . 12. . . . . . 12. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1 Array element operations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .2 Summary . . . . . . . .2. . . . . . . . . . . . . . . . .8. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .6 Binary sear h . . . . . . . . 12.10Exer ises . . . . . . . . . . .4 Histogram . . . . . . . . .1 Examples . . . .6. . .1. 12. . . . . . . . . . . . . . . . . . .2 Examples . . 12. . . . . . . . . . . . . . . . .1. . . . . 13. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1. . . . . . . . . . . . . . . . . . . . .2. . . . . . . .1 Time required . . . . . Default values of parameters . . . . . . . . 12. .1 Why onst de larations? . . . . . . . . . . . . . . . . . . . .1 Array: Colle tion of variables . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 158 158 159 160 162 162 164 164 165 166 167 168 168 169 170 170 171 171 172 173 174 178 179 179 181 181 181 183 184 184 186 188 188 190 191 191 191 192 196 196 197 197 199 .2. . . . . 12. . . . . . .4 Fun tion Calls involving arrays . .2 What we use in this book 12. . . . . .2. . . . . . . . . . . . 12. . . 12. . .1. . . . . . . . . . . . . 12. . . . . . . . .1 Notation for subarrays . . . . . . . . . . . . . . .8 Array Length and onst values . . . . .3. . . . . . . . . . . . . . . . . . . . .4. 12. . . . .2 Initializing arrays . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .2 A marks display program . . . . . .5 Sorting an array . . . . . . . .4. . . . . . . . . . . . . . . . . . . . . . . . . . . .6 A geometri problem . . . . . . . . . . .3 Chara ter string onstant . . . . . . . . . . . . . . . . . . . . . . 12. . . . . . . . . . . . . . . . . . . 12. . . . . .3 Who got the highest? . . . . . . . . . 12. . . . . . . . . . . . . ations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12. . . . . . 12. . . . . . . . . . .8. . . . . . . . . . . . . . . Exer ises . . . . . . . . . . . . . .2 The array name by itself . . . . . . . . . . . . .2. . . . 12. . . . . . . . . . 12 Arrays 12. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . Fun tion templates .3 [℄ as an operator . .2 Input . . . . . . . . . 12. . . . . . . . . . . 12. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .9 Summary . . .3 The inside story . . . . . . . . . . . . . . . . .1 Output . . . . . . . . . . . . . . .1 Out of range array indi es 12. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .5 A taxi dispat h program . . . . . . . . . . . . . 13. . . . . Fun tion overloading . . .1. . . . . .

14. . .1. .3. . . . . . . . . . . . . . 14. . 14.2. . . . . 14. . 13. . . . . . . .2 Exe ution example . . . .8 Exer ises .4. .1. . . .8 Stati member fun tions . . . . . . .3 Stru tures: advan ed features . . . . . . .4. . .1. . . . . . . . . 14.2 Pass by value or by referen e . . . . . . 13. . . . . . . .4. . . . . . . . .6. .2 Command line arguments to main . . . . . . . . . . . . 14. . . . .7 Generating permutations . . . . .4. . . . .4. . . . . . . .1 A ess spe i. . . . . . . . . 14. . . 13.1. . . . 2011. . . . 13.5 Arrays of stru tures .4. . . . . . . . . . . . . . . . . . .1. . . .4 Examples . . 14. . . 14 Stru tures and Classes 14. .6 All sour e shortest paths . . 14. . . . . . . . . . . . . .3. . . . . . . . . . . 14. . Do not distribute 13. .5 A queue data stru ture . 14. .3. . . . . . 6 Abhiram Ranade. . . . . . . . . . . . . . .6. 13. . . . 13. . . . .1 Call by referen e and onst de laration . . .2 Ordinary member fun tions . 14. . .2 Drawing polygons in simple pp .1 Visibility of stru ture names . 14. . .6 A ess Control . . . . . . . . .1. . . . . . . .4 A home-made 2 dimensional array .2 Stru tures and fun tions . . . . . . 13. . . . . . . . 13. . 13. . . . . . . . . .1 Algorithm . . . . . .1 Basi s of stru tures . . . . . 14. .2 Representing 3 dimensional ve tors . 14. . .4.1 Passing 2 dimensional arrays to fun tions . 13. . . 13. . . . . . . .4 Constant referen es . 14. . . . . . . . . . .6. 14. . . . . . .4. . . . .2. . .1 Constru tor fun tions . . . . . 14.4.3. . . . . . . . . 14. . . . . . . .6. . .4 Constru tors of nested stru tures . . . . . . . . 14. . . .2. . . . . . . . .3 Pointers to stru tures . . 13. . . . . . .5 Initialization lists .3 Default Constru tor . . 14. .3 Putting it together . . . . . . .6 Constant members . . . . .4 Additional issues .5 Linear simultaneous equations . .9 The this pointer . 13. . . . . . . .3 Explanation of the algorithm . 14. .1 Matrix multipli ation fun tion . .4. . . . . . . . . . . .7 Stati data members . .1 Operator overloading . . . . . . 14. .2 Default values to parameters .3 Two dimensional Arrays . . . . 14. 14. . . . . . . . .

.8 Header and implementation . 14. . . . . . . . . . . .6. . . . . . . 14. . . . . . . . . . . . .2 Friends . . .ers . . . . 14. . . . . . . . .7 Classes . . . . . . . . . . .

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 199 200 202 203 204 205 206 207 209 210 211 212 214 216 219 220 222 222 223 224 224 225 226 227 227 228 229 230 231 231 232 232 233 234 235 235 236 236 237 237 239 239 240 241 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .les . . . . . . . . . . . . . . . . . .

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . Exer ises . . . . .1 Main Program . . . . .1 Remarks .2. . . . . . . .2 Maintaining an ordered set . . 17. . . . . . . .4 15. . . .2. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14. .1 Layout of mathemati al formulae . . . . . . . . . . . . . . . . . . . . . . . . .5 15. . . . . . . . . . . . . . . . . . . . . . . .3 Exer ises . . 17. . 14. . . . . . . . . . . . . . . . . . . . . . . Do not distribute 14. . . . . . . . .1 A sear h tree . . . . . . . . . . . Compiling and exe ution . . . . . . . Con luding Remarks . . . . . . .11Exer ises . . . . . . . . . . . . 17 Stru tural re ursion . . . . . . . . . . . . . . .5 Drawing the pi ture . . . . . . . . . . . . . . . . . . .1. . . . . . . . . . . . .2. . .6 Balan ing the sear h tree . . . .1. . . . . . . . . . . . .2. . . . . . 17. . . . . . . . . . .1 Memory leaks . 17. . . . . . . . . . . . . 16. . . . . . . . .7 Remarks . .1 The Heap Memory . . . . . . . . . . . . . . . . . . . . . . . . . . . .8. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7 Abhiram Ranade. . . . . . . . . . . 16. . . . . . . . . . . . . . . . . . . . . . . . . . . . .4 A note about organizing the program . . . . . . . . . . . . . . . . . . .1 Stru ture of mathemati al formulae . . . . . . . . . . . . . . . . .10Graphi s . . . 16. . . . . 14. . . . 17. . . . . . . . . . 2011. . . . . . . . . . . . 16. . . . . . . . . . . . . .4. .5 Exer ises . . . . . . . . . . . 17. . . . . . . . . . 17. . 17. . . . .4 A simple safe solution . . . . . . . . . . . . . 16. . . . . . . . . . . . . . . . .3 Solutions . . . . . . . .1. . . 17. . . . . . . . . . . . .2 Representing mathemati al formulae in a program . . . . 242 243 243 244 244 246 246 249 250 252 253 254 255 256 257 258 258 262 263 264 265 268 268 271 272 273 273 275 276 280 281 281 282 282 284 285 287 287 288 288 . . . . . 17. . . . . . .3 15. . . . .2 Remarks . . . . . . . . . . . . . . . . . 16. . . . . . . . . The lass Star . . . . . . . . 16. . . . . . . . . . . 17. . . . . . . . 17. . . . . . . . . . . . . . . .1 Lifetime and a essibility . . . . . 15 A proje t: osmologi al simulation 15. . . . . . . . . . . . . . . . . .1. . . . . . . . . . . . . . 17. . .1. . . . . . . . . . . . . . . . . . . . .2. . . . . . . . . . . . . . . . .2. . . . 16. . . . . . . . . . . . . . . .2 A naive solution . . . . . . . . . . . . . . . . . . Mathemati s of Cosmologi al simulation Overview of the program . . . . . . . . . . . . . .2. . . . . . . . . . . . . .9 Template lasses . . . . . . . . .1. .3 Reading in a formula . . . . . .2 15. . . . . .6 16 Representing variable length entities 16.2. . .2 The general idea . . . . . . . . . . . . . . . . . . . . . . . . 17. . . . . . . . .2. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1 15. . . . . . . . . . . . . . .6 The omplete main program . .1 Separate ompilation 14. . . . . . 17. . . . . . . .2 Dangling Pointers . . . . .1. . . . . . . . . . . . . . . . 15. . . . . . . . . .8. . . . . . . . . .5 On the eÆ ien y of sear h trees . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17. . . . . . . . .1. . . . . . . . . . . . . . . . . . .3 The implementation . . . . . .4 Drawing the formula on the anvas . . . . . . . . . . . . . . . . . . . . . . . . . . . .

. . . . . . .2 Example 2 . . . . . .3. . . . . . . . . . . . . . . . . . .1.3 A Car lass . . . . . . . . . .2 Comparison of the two approa hes 20. . . . 19. . . . . . . . . . . . . . . .3.4. . . . . .4. . . . . . . . . . . . . . . .1 Finding and deleting map elements . . . . . . . . . . . 18. . . . . . . . . . . . . . . . . . . . . . . . . . . 20. . . . . . . . . . . . . . . . . . . . . . . . . . . . .4 Polymorphism and pointers . . . . . . . . . . . . . . . . . . . . . . . . . . . .3. . . . . . . . . . 18. .2 The Composite lass onstru tor . . . . . . . . . . . . .6 Customized sorting . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2011. . . . . . . . . . . . . . . . . . . . .1. . . . . 20 Inheritan e based design 20. .1 Inserting and deleting elements . .3. . . . . . . . . . . . . . . . . . . . . . . . . . . . 18. . . . 18. . . . . . .6 Exer ises . . 19. . . . . . . . . . . . . . . . . . . 18. . . . . 19. . .5 Other ontainers in the standard library . . . . . . . . . . . . . . . . . . 20. . . . . . . . . . . . 18. . . . . . . . . 19. . . . . . 18. . . . . . . . . . . . . . . . . . . . . . . .1. . . . . . . 19.3 Polymorphism and virtual fun tions . . . . . . . . . .1. . . . . . . .1. . . . . . . . 18. . . . . .3 General prin iples . . . . . . . . . . . .8 Use in the sort fun tion . . . . . . . . . . . . . . . . .2 Inserting and deleting ve tor elements 18. Do not distribute 18 The standard template library 18. . . . . . . . . . . . . . . . 19. . 20. .2 Time to a ess a map . . . . . . . . . . . . . . . . . . . . . . . . . . . 20. . . .3. . . .3. . . . . . . .4 Marks display variation 1 . . .1. . . 20. . . . . . . . . . . .5 Main program . . . . .4 Containers and Iterators . . . . . . . . . . .1. . . . . . .5 Abstra t Classes . . . . . . . . . 18. . . . . . . . . . . . . . . . . . . . . . . . . .2 The string lass . . . .1. .3.3. . . . . . . 18. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .4 Example 3 . . . . . .4. . . . . .1 The template lass ve tor .5 Marks display variation 2 . . . . . . . . . . . . . . . . . . . . . 20. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 19. . . . . . . . . .3. . 18. . . . . . . . . . . . . . . . . 19. . . . . . . . . . . .1 The message metaphor . . . . . . . .1 Example 1 . . . . .1 Marks display variation 3 . . . . . . . . . . . . .3 Sorting a ve tor . . . . .2 The simple pp graphi s system .1. . . . 18. . . . . . . 19. . 18. 18. . . . . . . . . . . . . . . . . . . . . . . . .3 Adding exponential expressions . . . . . . . . . . . . . . . . . . . . . . .3 The map template lass . . . . . . . . .1 Formula drawing revisited . . . . . . . . . . . . . . . .1. . . . 292 293 294 294 294 295 295 296 296 297 297 299 301 302 302 305 305 306 306 308 309 310 311 312 314 314 316 316 318 318 319 321 322 322 325 326 327 330 330 331 331 333 333 . . .1 Ownership . 18. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .6 Exer ises . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1. . . . . . . . . . . . . . . . . . . . . . . . . . . . . .4 Frames . . . . . . . . . . . . . . . .1 Basi design . . . . . . . .3. . . . . . . . . . . . . . . . . .2 Index bounds he king .3. . . . . . . . . . . . . . . . . . . . 19 Inheritan e 19. . . . . . . . . . . . . . . . . 18. . . .1 A ess rules and prote ted members . . . . . . . 8 Abhiram Ranade. . . . . .2 Constru tors and destru tors . . . . . . 20. . . . . . . 20. . . .7 Fun tion Obje ts . . . . . . . . . . 19. . . .3 Composite graphi s obje ts . . . . . . .

. . . . . . . . . . . . . . . . . . . 21. . . . . 2011. . . . . . . . 21.3 Simulating a oee sha k . . . . . . . . . . . . . . . . 21. . . 21.1 Airport on. . . . . . . . . . . . . . . . . . . . . . . . . . 22. . . .2 The restaurant simulation . 9 Abhiram Ranade. . . . . . . . . . . . . . . . . .3. . . . . . . . .1 Dijkstra's algorithm as a simulation . . 21.1 A Resour e lass . Do not distribute 21 Dis rete event simulation 21. . . . . .2 The simulation . . . . . . . . . . . . . .3.1 Dis rete event simulation overview . . . . . . .4. . . . . . . . .4 Single sour e shortest path . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21. . . . . . . . . . . . . . .

. . . . . . . . . . . . . .4. . . . . . .1 Formulation .2 S heduling strategy . . . . . . Creation and destru tion of variables Global variables . . . . . . . . .1 The general ase . . . . . . . . . .2. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1 The fun tion wakeup . . . . . . . . . . . . . . . . . . . . . . . . . .1. . . . . . . . . . . . . . 23. 22. . . . . . . . . . . . . . . . . . . . . . . . . . 22. . . . . . . . . .1 Main program and main data stru ture . . . .2 Implementation overview . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 22. . . . . . . . . . . . .2 B. . . . . . . .3 The fun tion getGate . . . 22. . . . . . . . . . . . . . .4. . . . . . . . . . . . . . . . . . . . . .2 Initial guess . . referen e variables .5 Deadlo ks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1. . . . . . . . . . . . .guration and operation . . . . . . . . . . . . . . . . . . . . . . . . .4 Blo ks . . . . . . . . . . . . . . . . . . . .2 How a ne kla e reposes . . . . . .3 Remarks . . . . . .3 Simulator input and output . . . . . . . 23. . . . . . . . 23. . . . . . . . . . . . 335 336 340 342 342 343 345 346 351 352 353 353 354 354 355 356 358 359 363 363 364 365 367 367 369 370 370 370 370 371 372 372 372 A Installing Simple pp 373 B S ope and Global Variables 374 B. . . . . . . 22 Simulation of an airport 23 Non-linear simultaneous equations 23. . . . . . . . . . . . . . . . . .2 The fun tion enter . . . . . . . . . . . . . . . . .1. . . .6 On Global variables vs. . . . . . . . . . . . . . . . . . .3 B. . . . . 23. . . . . . .1. S ope . . . . . . . . . .1 Safe operation rules . . . . . . . . . . . . . . . . . . . . . . .2. . . . . . . .1 B. . . . . . . . . . . 22. . . . . .4.3 Experien e . . . 22. . . . . . . . . . . . . . . . . . . . . . . . . . . 22. . . . . . . . . . . . . . . . . . . . . . . . . . . .3 The taxiway lass . . . . . . . . . . . . . . .2. . . . . . . . . . . . 22. . . . . . . .4 The plane lass . . . . . . . . .4 Exer ises . . . . . 22. . 23. . . . . . . . . . . . . . . . . . . . . . . . . . . . .1. . .3 Initial guess . . . .1 Newton-Raphson method in many dimensions 23. . . . . . . . . . . . . . . . . . . . . . . . . . . . . 22. . . . . . . . . . . . . . . 22. . . . . . 23. . . . . . . 374 374 376 376 . . . . . 23. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .2 Termination . . . . . . . . . . . . .2. . . . . . . . . . . . . . . . . . . . .1. . . . . . 22. . 23. . . . . . . . .

10 Abhiram Ranade. C. .2 General strategy . C. . C. . . . 2011. . . . . . . . . . . . Do not distribute C Managing Heap Memory C. .1 Referen e Counting .1 Syntheti example . .2 The template lass shared ptr . . .2. . . . . .2. . . . . .2. . C. .3 Shared pointer in derivative . . .

. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .3 Con luding remarks . C. . . . . . . . . . . . . . . . . . . . . . . . . . .4 Weak pointers . . . . . . . . . . . 387 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .1 Linking built-in fun tions . . . . . . . . . . . . .5 Solution idea . . . . . . . . . . . . . . . . . . . . . . . . . . . C. . . . . . . . .nding C. . . . . . . . . . . . . . . . . . .2. . . . . . . . . . . . . .0. . . . . 378 380 380 381 382 382 385 385 386 D Libraries 387 E IEEE oating point standard 389 F Reserved words in C++ 390 G Mis ellaneous operators 391 D. . . . . . . . . . . . . . . . . . . .2. . . . . . .

A few stages an be identi. Do not distribute Prefa e 11 Learning to program is like learning a natural language in many ways. Abhiram Ranade. 2011.

In some ways these stages are present even in learning programming languages. (d) ability to understand the literature of that language (e) write/speak reatively. ( ) write/speak formally. The . (b) being able to speak or write the language.ed in the pro ess of language learning: (a) being able understand spoken or written language.

languages). learly understanding ideas su h as ontrol ow. simpler.rst stage of programming language a quisition is understanding the syntax and semanti s of the language. Likewise. the two stages are not temporally disjoint. espe ially given the omplexity of languages su h as C++. in addition to expression skills. Through su h intera tion. analogous to speaking a natural language. the learner merely knows what ee t the exe ution of ea h statement has. It is not expe ted that the learner infers the intent in any way. is a noteworthy a hievement for any learner. This is by no means a trivial skill. when a learner speaks a language she is not only ommuni ating her thoughts. Su h experiments are extremely valuable for language a quisition. For programming languages. A learner must be en ouraged to try su h experiments from day one of the learning pro ess. Indeed. But even if we onsider a simple subset of the language (or onsider other. is one in whi h the learner starts writing programs. and they ome for free if you have a omputer. Of ourse. Suppose you have learned the Newton-Raphson method of . the analogous situation is as follows. There is of ourse more to expressing yourself in a language. Mastery of this basi ally enables the learner to simulate the exe ution of an arbitrary program using pen and paper. storage allo ation. someone learning C++ might write a simple program having just a single for statement to see if her understanding of the statement is orre t. s ope rules. her omprehension skills are aÆrmed. and an thus step through exe ution. The next stage. but also putting up her omposition for riti ism. keeping tra k of the program state by writing it down on paper if needed.

Can you write a program to .nding roots in a ourse in Mathemati s.

This an either be handled using a break onstru t. there exists a notion of a variable in mathemati s whi h is dierent and hen e an ause onfusion. To make matters worse. These are some of the skills to be learnt. The informal language using whi h algorithms are learned in mathemati s may not mat h the programming language. whereas the natural des ription of most pro esses require a loop exit somewhere in the middle. or by hoisting some ode out of the loop (often the more favoured style). Another diÆ ulty is presented by looping onstru ts: the standard onstru ts have a loop exit test at the beginning or at the end.nd the roots? What is required here is the ability to translate from the informal des ription of an algorithm learned in the mathemati s lassroom into the onstru ts provided by the programming language. This an be metaphori ally onsidered to be equivalent to the ability to reason formally about programs. This an be be ause of a variety of reasons. For example. The third stage is analogous to formal ommuni ation in natural languages. On the one hand this involves the ability to write down lear spe i. there is no equivalent of a programming language variable in traditional mathemati s.

ations (as opposed to having an intuitive idea) of the problem being solved. and reasoning with these spe i.

On the other hand. with parti ular emphasis on obje t oriented programming. The former opens up the entire area of formal . ations. this leads to various paradigms of program organization.

2011. Do not distribute 12 veri. Abhiram Ranade.

ation of programs. Given that formal veri

ation is not pra
tised by professional programmers, it is debatable how mu
h this should be stressed in an introdu
tory
ourse. We

feel, however, that even a beginner should understand that in prin
iple, programs must be

proved
orre
t, and that there exist te
hniques for doing this. Notions su
h as pre
onditions,

post
onditions and invariants must be understood. It is felt that these ideas will sub
ons
iously guide the student into writing better programs, even if they are found too laborious

to implement rigorously at the present time. As to programming paradigms, our approa
h is

somewhat pragmati
. At every point in the book we have tended to
hoose a programming

style whi
h appears most appropriate for the job at hand, given the tools the student has.

From time to time we have given alternate ways of writing a program. However, there is a

progression towards obje
t oriented programming. It has happened as a byprodu
t of the

requirements, rather than be
ause of the goal of following a stylisti
di
tat.

The fourth stage is analogous to reading good literature. What is the point of learning a

new language if not to read something ex
iting written in it? For programming this means

a
quiring some familiarity with some
lassi
al algorithms. We have made a
ons
ious eort

in this book to a
quaint the reader with interesting
omputational problems in a variety of

areas, from mathemati
s and physi
al s
ien
es to operations resear
h. Of
ourse, this barely

s
rat
hes the plethora of elegant algorithms that
ould be ex
iting for the reader. Our hope

is merely that it will
reate a taste and ex
itement in the reader to seek out
omputations

and algorithms. We will have served our purpose, for example, if this book
auses readers

to want to learn more about
osmologi
al simulation, or optimizing airport layouts, or data

stru
tures or error analysis in numeri
al algorithms.

The

**nal stage, the ability to design new algorithms, is perhaps analogous to
reative
**

writing in natural language. Algorithm design is a vast subje
t, and there are huge tomes

written on it. But we feel that an introdu
tion to programming and problem solving must

ontain a des
ription of the most primitive and yet perhaps the most powerful problem

solving idea: re
ursion. We have attempted to give a somewhat detailed introdu
tion to

re
ursion using several examples. Re
ursion is important not only as an algorithm design

tool, but also as a me
hanism for expressing programs: several programs are more elegant

when expressed re
ursively. We have also
onsidered memoization as a natural optimization

for re
ursion, and so we
ould have said to have tou
hed upon the te
hnique of dynami

programming as well. The se
ond theme in our presentation
on
erns the use of exhaustive

sear
h. Exhaustive sear
h
an be expressed
leanly using re
ursion, and hen
e it is a good

testing ground to exer
ise re
ursion. More importantly, we feel that it reassures the student

of the power of
omputer programs by expanding his vision of what
an be solved using

omputers.

Most of the book, enough to learn basi
s of C++, is meant to be a
essible to students

who have passed standard X. Some se
tions are addressed more to s
ien
e and engineering students. However, I would like to mention that when I taught a
ourse based on this

material several students
ame up and said that the programming exer
ises related to advan
ed mathemati
s topi
s a
tually helped them understand the mathemati
s topi
s better.

So even if you feel mathemati
s is not your strong point, you may still want to read the

mathemati
ally involved se
tions of the book with an optimisti
attitude.

I feel that a
ourse in programming should ex
ite the problem solver in you, and you

should feel a sense that everything is solvable, not just grand problems but even mundane

Abhiram Ranade, 2011. Do not distribute

13

**problems (more useful and often as diÆ
ult!). If this book
an en
ourage you to view day
**

to day problems as
omputation, and give you the
on

**den
e that you
an write programs
**

to ta
kle them, this book will have served its purpose.

Chapter 1

Introdu
tion

A
omputer is one of the most remarkable ma
hines invented by man. Most other ma
hines

have a very narrow purpose. A wat
h shows time, a
amera takes pi
tures, a tru
k
arries

goods from one point to another, an ele
tron mi
ros
ope shows magni

**ed views of very small
**

obje
ts. Some of these ma
hines are mu
h larger than a
omputer, and many mu
h more

expensive, but a
omputer is mu
h, mu
h more
omplex and interesting in the kind of uses

it
an be put to. Indeed, many of these ma
hines, from a wat
h to an ele
tron mi
ros
ope

typi
ally might
ontain a
omputer inside them, performing some of the most vital fun
tions

of ea
h ma
hine. The goal of this book is to explain how a
omputer
an possibly be used

for so many purposes, and many more.

Viewed one way, a
omputer is simply an ele
tri
al
ir
uit; a giant,
omplex ele
tri
al

ir
uit, but a
ir
uit nevertheless. In prin
iple, it is possible to make
omputers without the

use of ele
tri
ity { indeed there have been designs of
omputers based on using me
hani
al

gears, or
uidi
s devi
es. But all that is mostly of histori
al importan
e. For pra
ti
al

purposes, today, it is

pro essing it. Or we ould mean a tivating a beeper onne ted to your omputer if the movement dete ted is deemed suspi ious. Finally. pressure. determining whether the signals re eived from a light sensor indi ate that there is some movement in the vi inity of the sensor.ne to regard a omputer as an ele tri al ir uit. remembering it so that it an be reprodu ed later. Exa tly whi h parts of the ir uit are a tive at what time is de ided by a program fed to the omputer. By data we ould mean dierent things. In this hapter. It ould also mean something mu h more omplex: e. Or it ould mean ele tri al signals a omputer an re eive from a sensor whi h senses temperature. It is the program whi h distinguishes a omputer from most other ma hines.e.g. Parts of this ir uit are apable of re eiving data from the external world. How to develop these programs is the subje t of this book. by \send data to the external world" we might mean something as simple as printing the al ulated average on the s reen of your omputer so that you an read it. light intensity and so on. For example. we will begin 1 Also it is appropriate to think of our own brain as a omputer made out of biologi al material. i. 1 14 . neurons or neural ells. by installing dierent programs the same omputer an be made to behave in dramati ally dierent ways. and sending the results ba k to the external world. The word pro ess might mean something as simple as al ulating the average of the sequen e of numbers you type from the keyboard. it ould mean some numbers you type from the keyboard of a omputer.

or even develop (typi ally alled write) programs without knowing a lot about the spe i. Abhiram Ranade. Do not distribute 15 by seeing an example of a program. It turns out that we an understand. 2011.

When you are learning to drive. But in a few hapters. it is better to start with a simpler vehi le. learly one an learn to drive without knowing how exa tly an automobile engine works. ir uits that the omputer ontains. you will outgrow simple pp and be able to use standard C++ (like \the pros"). 1. There are many languages using whi h programs an be written. in whi h there arent too many onfusing ontrols. but yourself write some programs. unless of ourse you are using the graphi s features. invented in the early 1980s by Bjarne Stroustrup. For the initial part of the book. The pa kage simple pp does ontain this feature. we will not use the bare C++ language. it ould be said that C++ is like a omplex ra ing ar. The language we will use in this book is the C++ programming language. To use the driving metaphor again. This is very similar to how one might learn to drive a ar. We developed this pa kage so that C++ appears more friendly and more fun to people who are starting to learn C++.1 A simple program Our . We thus expe t that by using the simple pp pa kage it will be easier and more fun to learn the language. Also. but instead augment it with a pa kage alled simple pp (whi h stands for simple C++) whi h we have developed. So you will be able to not only understand the program that we show you. How to install this pa kage is explained in Appendix A. standard C++ does not by default ontain the ability to draw pi tures.

loseTurtleSim(). left(90). } wait(5). forward(100). #in lude <simple pp> main_program{ turtleSim(). left(90). forward(100).rst example program is given below. it will . forward(100). If you exe ute this program on your omputer. forward(100). left(90).

Then the turtle will move and draw lines as it moves. Then a small triangle whi h we all a turtle will appear in the window. 2 2 Our turtle is meant to mimi the turtle in the Logo programming language. and the program will end. Shortly we will des ribe how to exe ute the program. the window will vanish. After that. .rst open a window. The turtle will draw a square and then stop.

16 Abhiram Ranade. The . and this will help you modify the program to make it do something else if you wish. 2011. Do not distribute First we will tell you why the program does all that it does.

The turtle is equipped with a pen. main programf. The amount is to be given in pixels. (). Other numbers ould also be spe i. Sin e the pen was down. your s reen is really an array of small dots. Typi al s reens have an array of about 1000 1000 dots. The next line forward(100) auses the turtle to move forward by the amount given in the parentheses. The line following that. turtleSim() auses a window with a triangle at its enter to be opened on the s reen.rst line #in lude <simple pp> de lares that the program makes use of some fa ilities alled simple pp in addition to what is provided by the C++ programming language. then it draws on the ground as the turtle moves. As you might perhaps know. the pen of the turtle is lowered. says that what follows is the main program. the turtle points in the East dire tion. If the pen is lowered. Initially. The main program itself is ontained in the bra es f g following the text main program. and it is ready to draw. The ommand left(90) auses the turtle to turn left by 90 degrees. ea h of whi h an be of any olour. So the ommand forward(100) auses the turtle to go forward in the urrent dire tion it is pointing by about a tenth of the s reen size. Ea h dot is alled a pixel. whi h an either be raised or lowered to tou h the ground. The triangle represents our turtle. The next line. and the s reen the ground on whi h it an move. Initially. this auses a line to be drawn.

Sin e the turtle is fa ing north this time. and the fourth forward(100) .ed instead of 90. the line is drawn northward. After this. the next ommand is forward(100). Then the turtle turns on e more be ause of the third left(90) ommand. The next left(90) ommand auses the turtle to turn again. whi h auses the turtle to move forward by 100 pixels. The following forward(100) draws the third side. This ompletes the se ond side of the square.

e. the program halts. The explanation is simple. A ommand in C++ will typi ally require additional information to do its work.nally draws the fourth side and ompletes the square. This is the time you have to admire the work of the turtle! Finally the last line loseTurtleSim() auses the window to be removed from the s reen. Hen e we need to simply write ().g. we must .1 Exe uting the program To exe ute this program. in this ase we simply put the pie es inside () separated by ommas. After exe uting this line. Later you will see that there an be ommands whi h will need more than one pie es of information. for the forward ommand. Perhaps you are puzzled by the () following the ommands turtleSim and loseTurtleSim. After this the line wait(5) auses the program to do nothing for 5 se onds. you need to spe ify a number denoting how far to move. 3 1. It just so happens that turtleSim and loseTurtleSim do not require any additional information.1.

rst have it in a .

pp for . It is ustomary to use the suÆx .le on your omputer.

So let us suppose you have typed the program into a .les ontaining C++ programs.

pp { you an also get the .le alled square.

as you will see later.le from the CD or the book webpage. there an be non-main programs too. . 3 Yes.

Do not distribute 17 Next. we must ompile the . 2011. Abhiram Ranade.

e. i.le. translate it into a form whi h the omputer understands more dire tly and an exe ute. The translation is done by the ommand s++ whi h got installed when you installed the pa kage simple pp. whi h must be present on your omputer (See Se tion A). The ommand s++ merely invokes the GNU C++ ompiler. In a UNIX shell you an ompile a .

le by typing s++ followed by the name of the .

le. As a result of this another . In this ase you would type s++ square. pp.

le is produ ed. this . On UNIX. whi h ontains the program in a form that is ready to exe ute.

le is typi ally alled a.out. This .

1 Exe ution order Another important similarity on erns the order of the senten es and ommands. It is a eptable to put in spa es and linebreaks almost anywhere so long as words or numbers are not split or joined.le an be exe uted by typing its name to the shell % a. put leading spa es before lines that are part of main program.2.out You may be required to type . This exibility is meant to enable you to write su h that the program is easy to understand. . top to bottom. indentation is also used in normal writing in English. Note that while most human beings will tolerate writing in whi h a full-stop is missed. you should see a window ome up. We see an example next. Note however. As you might observe. the order in whi h the ommands of a program are exe uted an be hanged.forward(100) left (90 ). A paragraph onsists of senten es separated by full stops. A paragraph is expe ted to be read from left to right. But just as you have dire tives in magazines or newspaper su h as \Please ontinue from page 13.2 Remarks A C++ program is similar in many ways to a paragraph written in English. 1. Thus it is perfe tly legal (though not re ommended!) to write turtleSim(). . This is again done to make it visually apparent what is a part of the main program and what is not. Thus the ommands whi h a tually draw the square are separated from those that open and lose the windows. By default a omputer exe utes the ommands left to right./a. with the turtle whi h then draws the square. that the omputer is more forgiving about the use of spa es and line breaks. ea h ommand must be followed by a semi- olon.e. Or you may be able to exe ute by double li king its i on. So is a program. i. olumn 4". a C++ program ontains ommands whi h must be separated by semi- olons. top to bottom. if you wish. Another important idea is to indent. we have put empty lines in the program so as to help ourselves while reading it. When the program is thus exe uted. 1.out be ause of some quirks of UNIX. Indeed. a omputer is very fastidious.

Ea h exe ution of the body is said to be an iteration. repeat(10){ forward(100). 1. say a de agon. This works. ount ould be any number. The statements ould be any sequen e of statements whi h would be exe uted as many times as the expression ount.1 Drawing any regular polygon Our next program when exe uted. } This program. Abhiram Ranade. left(36). The statements are said to onstitute the body of the repeat statement. The main dieren e will be that we should turn by 36 degrees. 2011. . Only after that we exe ute loseTurtleSim(). Its general form is repeat( ount){ statements } In this. and then draws the required polygon. #in lude <simple pp> main_program{ turtleSim(). Only after the body of the loop is exe uted as many times as the value of ount. out << "Type in the number of sides: ". Here is what you would write instead.3 Repeating a blo k of ommands At this point you should be able to write a program to draw any regular polygon. in the given order. you dont need to do that. #in lude <simple pp> main_program{ int nsides. And then we just repeat the ommands as many times as needed. So in this ase the sequen e forward(100). asks the user to type in how many sides the polygon should have. Do not distribute 18 1. in >> nsides. drawing all 10 edges of the de agon. do we exe ute the statement following the repeat statement. will draw a de agon. rather than 90 degrees. } loseTurtleSim().3. Indeed. is exe uted 10 times. but you may get bored writing down the same ommand several times. left(36). The new statement in this is the repeat. when exe uted. turtleSim().

} wait(5). 2011. left(360. Do not distribute } 19 repeat(nsides){ forward(50). This program has a number of new ideas.0/nsides). Abhiram Ranade. loseTurtleSim(). The .

rst statement in the main program is int nsides. The . whi h does several things.

This statement is said to de. it also gives a name to this region: nsides.rst word int is short for \integer". whenever the programmer uses the name nsides it should be onsidered to refer to this region. It is ustomary to say that nsides is a variable. and it asks that a region be reserved in memory in whi h integer values will be stored during exe ution. Se ond. Finally it de lares that from now on. whose value is stored in the asso iated region of memory.

As many variables as you want an be de.ne the variable nsides.

ned. either by giving separate de.

int nsides.nition statements. or by writing out the names with ommas in between. length. would de. For example.

ne two variables. the .

The sequen e of hara ters << denotes the operation of writing something on the s reen. out is a name that refers to the omputer s reen. We will learn more about names and variables in the next hapter. The next new statement is relatively simple. What gets written is to be spe i.rst alled nsides. It is ustomary to pronoun e the in out (and in in the next statement) as \see". the se ond length.

the name in refers to the keyboard. The user must type in an integer value followed by typing the return key. you may put in a dierent message in your program. Of ourse. It asks the omputer to wait until the user types in something from the keyboard. So the statement in our program will display the message Type in the number of sides: on the s reen. In the statement after that. in >> nsides. and whatever is typed is pla ed into the (region asso iated with) the variable nsides. The value typed in gets pla ed in nsides. After the in >> nsides. and that will get displayed. Exe uting a repeat statement is nothing but exe uting its body as many times as spe i. the omputer exe utes the repeat statement.. statement is exe uted.ed after the <<.

then the variable nsides would have got the value 15. The loop body onsists of the two statements forward(100) and left(360. Thus in this ase the omputer will divide 360. and the result is the turning angle.ed. .0/nsides).0 by the value of the variable nsides. Noti e that instead of dire tly giving the number of degrees to turn. if nsides is 15. This is allowed! The omputer will evaluate the expression. we have given an expression. and the loop body would be exe uted 15 times. So if the user had typed in 15 in response to the message asking for the number of sides to be typed. In this ase. the omputer is asked to exe ute the body nsides times. the turning angle will be 24. Thus. and use that value. So it should be lear that in this ase a 15 sided polygon would be drawn.

left(360. How does a omputer exe ute this? Its rule is simple: to exe ute a repeat statement.0/nsides). The key new idea in this program is the appearan e of a repeat statement inside another repeat statement. 2011. Do not distribute 20 1. in >> nsides. } } loseTurtleSim(). } repeat(10){ out << "Type in the number of sides: ". Abhiram Ranade. turtleSim().2 Repeat within a repeat What do you think the program below does? #in lude <simple pp> main_program{ int nsides. it just exe utes the body as many times as spe i. repeat(nsides){ forward(50).3.

the required number of edges will be drawn by the inner repeat statement. after the user types in the number. the next iteration of the outer repeat would begin. penUp(): This auses the pen to be raised.4 Some useful turtle ommands The following ommands an also be used. So after exe uting this ommand. In ea h iteration of the outer repeat statement there will one exe ution of the inner repeat statement. 1. in this ase a single iteration of the outer repeat will ause the user to be asked for the number of sides. But one exe ution of the inner repeat ould have several iterations. Thus. one on top of another.ed. After that. There is nothing inside the () be ause no number is needed to be spe i. for a total of 10 iterations. the turtle will move but no line will be drawn until the pen is lowered. Thus a total of 10 polygons would be drawn.

forward(5). penDown(). forward(10).g. until the pen is raised again. 1.g a dashed line will be drawn. penDown(): This auses the pen to be lowered.ed. penUp(). e. a line will be drawn whenever the turtle moves. So after exe uting this ommand. Thus if you write repeat(10)fforward(10).5 Numeri al fun tions The ommands you have seen so far for ontrolling the turtle will enable you to draw several interesting . as was the ase with forward.

gures. However you will noti e that it is umbersome to draw some simple .

Do not distribute 21 . Abhiram Ranade. 2011.

or the square root of a number? The answers to these questions will ome later. If you want to . then you will need to take square roots { and we havent said how to do that. For now you an just use the following ommands without worrying about how the al ulation a tually happens. how does a omputer al ulate the value of the sine of an angle. Let us start with square roots.gures. We now provide ommands for these and some ommon operations that you might need. Say you want to draw a simple right angled triangle with side lengths in the proportion 3:4:5. For example. To spe ify the angles would require a trigonometri al ulation. You may wonder. if you wish to draw an iso eles right angled triangle.

So for example. forward(100). An important additional ommand is ar tan2. and will be used in pla e of the ommand.500 as follows. writing tangent(45) will be as good as writing 1. As you might guess. exp. Now you will be able to do a triangle with side lengths 300.5) will be 60 as expe ted. left(90). You simply write sqrt(x) in your program and during exe ution. pow(x.x) will return the inverse tangent of y/x in the full range. forward(300). Some other useful ommands that are also provided: 1. This an be done by looking at the signs of y and x. the square root of x will be al ulated.-1) would be 135.1) would be -45.-4)). left(135). These will take a single number as an argument and will return an angle (in degrees). log10 : These return respe tively for argument x the value of ex (where e is Euler's number. we an put expressions into arguments of ommands. The ommands for omputing trigonometri ratios are sine. here is how you an draw an iso eles right angled triangle. Thus ar tan2(1. Ea h of these take a single argument: the angle in degrees. forward(400). ar osine(0. Writing ar tan2(y. left(ar tan2(3. and ar tan(-1/1)=ar tan(1/-1)=ar tan(-1) would also be -45. 2. while ar tan2(-1. pow : This takes 2 arguments. This needs two arguments. forward(500). -180 to +180. These ommands return the angle in the range -90 to +90. forward(100). So for example. log.nd the square root of a number x. The ommands for inverse trigonometri ratios are ar sine. . and put the ommands themselves into other expressions and so on. For example. the base of the natural logarithm). forward(100*sqrt(2)). osine and tangent. y and x respe tively.400. ar osine and ar tan. left(90). then the ommand for that is sqrt. the natural logarithm and the logarithm to base 10.y) returns xy . information whi h would be lost if the argument had simply been y/x.

2011. the program is said to loop through the body for the required number of iterations. At this point you should also see why the notation used to write programs is alled a language. Do not distribute 1. and obje t. or there an be lauses.6 Con luding Remarks 22 At this point you should have some idea of what a omputer program is and how it exe utes: starting at the top and moving down one statement at a time going towards the bottom. many. obje ts and other lauses. the program exe utes the body of the loop several times. A spoken language is very exible and general. And so long as the stru ture is respe ted. there is a subje t.g. verbs. indeed an in. you an have many. whi h an themselves ontain subje ts. It has a grammati al stru ture. If there are repeat statements. e. verb. Abhiram Ranade.

Similarly. Indeed our treatment of the C++ programming language will be somewhat similar to how you might be taught Tamil or Fren h. Hope you will . e.nite number of senten es.g. we will introdu e the C++ language as we try to solve more and more interesting omputational problems. Just as language learning is more fun if you read interesting literature. but inside the body there an be other statements in luding a repeat statement. omputer programs have a stru ture. a repeat statement must be followed by a ount and a body.

So for example. The omputer will evaluate those expressions and use the resulting values. it will also be important for you to develop some intuition for what the rules might be or ought to be. is this a general rule? It turns out. These you will master with some pra ti e. you may also spe ify expressions. and it is worth stating them expli itly.nd this enjoyable. an expression su h as 360. In most pla es where numbers are expe ted. how to group them into repeat statements. that this is a general rule. The . of ourse. However. what order to give the ommands in. It will be important to learn the various grammati al rules of the C++ language as you go along. indeed. You should ask yourself. the grammati al rules of C++. The main diÆ ulty is in de iding what ommands to give. The major diÆ ulty in writing programs is not. we said in the se tion above that instead of spe ifying a number for how mu h to turn. For example. whi h will ause the perimeter of the polygon being drawn to be printed on the s reen (assuming the side length is 100).0/nsides an be used. you may write out << nsides*100. two ideas have appeared regarding this. In this hapter.

programming is a bit like tea hing. In some sense. then you repeat the same draw-turn pattern four times. . So this has two parts: you should yourself know how to solve the problem. Seeing this pattern is extremely important.rst idea is: before you starting to write a program that makes a omputer do something. there are likely to be patterns or symmetries in it. and you should be able to explain in words how you solve the problem. How would you draw a square? How would you draw a square sitting on top of a real turtle? You will realize that what you write is often just a areful statement of what you yourself would have done. think about how you yourself solve the problem. The pattern ontains some insight about the a tivity whi h is inherently valuable. Writing ompa tly and su h that the patterns in the a tivity are re e ted in the program is a major goal of programming. The se ond idea is: whatever a tivity you are doing. but more dire tly it enables us to write ompa t programs. If you are drawing a square.

starting from the least ambitious going on to the most ambitious: 1. We will try to get an intuitive sense of omputer hardware so that the working of a omputer as will be dis ussed in subsequent hapters appears reasonable to you. and you do not feel that there is too mu h magi in all this. For example. Understanding the dierent statements in C++. Here are some of the possible interpretations. Do not distribute 23 1. The subsequent hapters will tea h you how to program using C++. Ability to write programs to solve problems that you an yourself solve using pen il and paper and given enough time.7 Overview of the book The next hapter gives you a bird's eye view of the world of omputers and programming. 2011. we know the formula for . 2. and how real life problems from playing hess to making train reservations an be represented on them. Another way of stating this is: given a program and enough time. The phrase \how to program" an have many interpretations. an you in prin iple say what output the program will if you know what input is given to it? The issue here is only omprehension. and not design. We will study at a high level how omputers are onstru ted. Abhiram Ranade.

4 . Dis overing new ways of solving a problem. For example. and you are better able to say things whi h you didnt know how to say earlier. Solving su h problems requires a higher level of problem solving/programming ability. This is dierent from merely being able to onverse on the street. but that is only in a manner of speaking. This is perhaps the analogue of the fourth point mentioned above: ability to solve new problems. Cooperate with a team of people to solve a large problem. and gauge your own progress along these dire tions. we would be determine the average mark. then you have rea hed the se ond level of programming ability. It is hoped that you will keep these analogies in mind as you read the book. The situation is not unlike learning a foreign language. Can we express this omputation in a program? Or given the set of marks obtained by students in a ourse. in that ulture. you need to learn the etiquette. however. how to do your work so that others an use it be ome important. even people who fully understand omputers think there is something magi al in them. 4 Well. what is the shortest way to go from Mumbai to Tanjore. 4. spending at most Rs 1000? You may think you know many ways to make this travel. Of ourse. when you learn a new language. Often. Can we write a program to do su h omputation? There are many su h problems whi h you solve routinely without omputers. Issues su h as how to de ompose the problem. the way to say things formally. Being able to understand the language is one level of ompeten e. be ause you have a systemati pro edure in mind.nding the roots of a quadrati equation. or the maximum mark. it is quite likely that you may not know enough to be sure that no better way is possible. Can you express these rules in programs so that the problems an be solved by a omputer? If the answer is yes. your general expression abilities improve as you learn a new language. 3. Being able to speak it is the next.

2011. you must write many.1 A note regarding the exer ises Programming is not a spe tator sport. Another important suggestion: while reading many times you may . Abhiram Ranade. That is when you will dis over whether you have truly understood what is said in the book. Do not distribute 24 1. To this end. many programs yourself. whi h you should assidously solve.7. we have provided many exer ises at the end of ea h hapter. To really understand programming.

While the author will not be present to answer your questions. \What if we write this program dierently". there is an easy way to .nd yourself asking.

Use this idea to draw the numeral 8 { two ir les pla ed tangentially one above the other. then it will look essentially like a ir le. Draw a sequen e of 10 squares. 3.nd out { write it dierently and run it on your omputer! This is the best way to learn. i. one to the left of another. Modify the program given in the text so that it asks for the side length of the polygon to be drawn in addition to asking for the number of sides. say 100. A pentagram is a . 1. and use repeat statements to write a on ise program as possible. 5. If you draw a polygon with a large number of sides. 2. Draw a hessboard. 1. a square of side length say 80 divided into 64 squares ea h of sidelength 10. 4. you are expe ted to identify the patterns/repetitions in what is asked. You should also avoid ex essive movement of the turtle and tra ing over what has already been drawn. In fa t this is how ir les are drawn: as a many sided polygon.8 Exer ises In all the problems related to drawing.e.

Spe i.ve pointed star. drawn without lifting the pen.

then this is the .D. let A.B.E be 5 equidistant points on a ir le. ally.C.

7.0" in our program rather than just \360". 6. But you ould have some fun . Draw this. There is a reason for this whi h we will dis uss later. We wrote \360. Draw a seven pointed star in the same spirit as above.gure A{C{E{B{D{A. Note however that there are more than one possible stars.

instead of . Rewrite the program using just \360" and see what happens..guring it out.?" { you should simply try it out! 8.0/11.. A more dire t way is to put in statements out << 360/11.. Read in the lengths of the sides of a triangle and draw the triangle. You will need to know and use trigonometry for solving this. out << 360.. and see what is printed on the s reen. . This is an important idea: if you are urious about \what would happen if I wrote .

When you hold a set of ards in your hand. Do not distribute 25 9. only a triangular portion of ea h ard is seen. Abhiram Ranade. 2011. In parti ular. you usually arrange them fanned out. Now. but the other ards are seen only partially. we an see the top ard ompletely. Say you start with ards sta ked one on top of the other. Then you rotate the ith ard from the top by an amount proportional to i (say 10i degrees to the left) around the bottom left orner. with the top left orner being at the apex of ea h triangle. This is the .

(a) Draw it assuming the ards are transparent. In both ases. .gure that you are to draw. For this some trigonometri al ulation will be ne essary. use repeat statements to keep your program small as possible. (b) Draw it assuming the ards are opaque.

Chapter 2 A bird's eye view At .

rst glan e. or help design ars. it is indeed surprising that a single devi e like a omputer should be able to predi t the weather. or analyze pi tures. or sear h the books and do uments all over the world and tell you where you might .

or play hess better than the human world hampion. The argument has two parts.nd information regarding your topi of interest. The purpose of this hapter is to redu e this surprise somewhat. The . to make it more believable that a omputer ould perhaps be able to do this.

then ould be said to be founded on two great s ien es. we have Mathemati s. from predi ting the weather to playing hess. Ele tri al Engineering. On e we have redu ed the problem we want to solve to some mathemati al problem. We wish to des ribe the relationship of programming to these s ien es. many problems simply by running appropriate programs. and on the other side. we have the s ien e of designing ele tri al ir uits. espe ially that related to ir uit design. Mathemati s. is apable of solving many. Mathemati s is universal.rst part is the observation that all the problems des ribed above. then what remains is to devi e a ir uit whi h an solve the problem. Even in this. On one side. an be des ribed in the language of numbers. will be quite super. there is an element of universality: we will argue that a single (but huge) ir uit that a modern omputer is. Our des ription. The s ien e of programming. In a sense. it an be used to analyze almost every phenomenon or pro ess or entity known to man.

ial. as you navigate through subsequent hapters. However. We dis uss this brie y and we will return to this question in later hapters. The rest of the hapter attempts to provide a plausible view of the ir uits onstituting a omputer. it is hoped that this des ription will provide some ba kground. a helpful reassuran e. We present a very simpli. We begin with the question of representing real life phenomenon using numbers.

**ed model of a
omputer and using it explain some basi
ideas su
h as
**

the notion of a program stored in memory, the idea of step by step exe
ution of instru
tions,

and the notion of an address for referring to regions of memory. These ideas are
entral to

design of
omputers as well as programming.

We expe
t our des
ription of
omputers in this
hapter to be read like a short, popular

s
ien
e arti
le. We will try to anti
ipate the main questions you might have about how

omputers work, and answer them at an intuitive level. We will gloss over many details,

and also oversimplify several ideas. We
annot give a
omplete answer to all questions, after

all,
ir
uit design and
omputer ar
hite
ture are deep subje
ts, ea
h needing an independent

book or more. We believe, however, that you will get a \working knowledge" of
omputer

26

27

Abhiram Ranade, 2011. Do not distribute

0

0

0

1

1

1

1

0

0

0

(a)

0

0

1

0

0

0

0

1

0

0

0

1

0

0

1

0

0

0

1

0

1

0

0

0

0

0

1

0

0

1

1

0

0

0

0

0

1

0

0

1

(b)

1

0

0

0

0

0

1

0

0

1

0

1

0

0

1

0

0

0

1

0

0

1

0

0

0

0

0

0

1

0

0

0

1

1

0

0

1

1

0

0

0

0

0

0

1

1

0

0

0

0

(c)

**Figure 2.1: A pi
ture, its representation, and re
onstru
tion
**

hardware, providing adequate ba
kground for the study of programming to
ome later.

2.1 Representing real life entities using numbers

**Some entities in real life have an obvious mathemati
al
hara
ter; any quantity that we
an
**

measure, su
h as mass, for
e, voltage,
on
entration of
hemi
als, is naturally expressed

numeri
ally. But for some other entities, it is not immediately obvious how they
an be

expressed using numbers. Can we express pi
tures or language using numbers? We dis
uss

these questions brie
y.

Here is how a pi
ture might be represented using numbers. Consider a bla
k and white

pi
ture to begin with. The pi
ture is divided into small squares by putting down a

ne

grid over it, as in Figure 2.1(a). Then for ea
h small square we determine whether it is

more white or more bla
k. If the square is more white we assign it the number 0, if it is

mostly bla
k, we assign it the number 1. So if we have divided the pi
ture into m n

small squares (pixels), m along the height and n along the width, we have a sequen
e of mn

numbers, ea
h either 1 or 0 that represents the pi
ture. Figure 2.1 shows the numbers we

have assigned to ea
h square. Given the mn number representation, we
an re
onstru
t the

pi
ture as follows: wherever a 0 appears, we leave the
orresponding square white, wherever

a 1 appears, we make the
orresponding square bla
k. The re
onstru
tion, using the numbers

in Figure 2.1(b) is shown in Figure 2.1(
). As you
an see, the re
onstru
ted pi
ture is not

identi
al to the original pi
ture, but reasonably similar. By
hoosing a

**ner grid, we would
**

have been able to get a better approximation of the original pi
ture. Sin
e our eye
annot

individually see very small squares, it turns out that pixels of size about 0.1 mm are good

enough, i.e. the re
onstru
ted pi
ture is hard to distinguish from the original. Pro
essing

a pi
ture means doing
omputations involving these numbers. For example,
hanging every

zero to a one and vi
e versa, will
hange the pi
ture from \positive" to \negative"!

The idea of putting down a grid over the obje
t of interest is very powerful. Suppose

we wish to represent the worldwide weather. Typi
ally, we divide the surfa
e of the globe

into small regions. For ea
h region we
onsider all the parameters relevant to the weather,

e.g. the ambient temperature, pressure, humidity. Of
ourse, all points in a region will not

have identi
al temperature, but we nevertheless
an
hoose an approximate representative

temperature, if the region is reasonably small. The key to predi
ting weather are laws of

physi
s: given the
urrent state and knowing the physi
al
hara
teristi
s we
an say what the

next state will likely be. This is a very gross simpli

ation of how the weather is predi ted,

Abhiram Ranade, 2011. Do not distribute

28

**but, it is
orre
t in essen
e.
**

Text
an also be represented using numbers. Essentially, we devi
e a suitable
ode.

The most
ommon
ode is the so
alled ASCII (Ameri
an Standard Code for Information

Inter
hange)
ode. In this, the letter \a" is represented as the number 97, \b" as 98 and so

on. Standard symbols and the spa
e
hara
ter also have a
ode assigned to them. So the

word \
omputer" is represented by the sequen
e of numbers 99,111,109,112,117,116,101,114.

Thus we might be given a sequen
e representing a paragraph. Finding whether a given

word o
urs in this paragraph is simply
he
king whether one sequen
e of numbers is a

subsequen
e of another sequen
e of numbers! On
e we
an express text, we have a foothold

for expressing senten
es, and all of language! The ASCII
ode is meant only for the Roman

alphabet, there are
odes meant for other alphabets, su
h as the Devanagari alphabet as

well.

We will see more real life obje
ts (and mathemati
al obje
ts too, su
h as sets, fun
tions)

and how to represent them in the rest of the book.

1

**2.2 Representing numbers on a
omputer
**

God made natural numbers, the rest is the work of man.

{ Leopold Krone
ker.

**There are, of
ourse, dierent types of numbers. Starting with the simplest, the so
**

alled natural numbers or
ounting numbers, we have integers (whi
h
an be negative),

rational numbers, real numbers, and even
omplex numbers. We begin by dis
ussing how

to represent natural numbers. The other types of numbers
an in fa
t be represented using

natural numbers. Note that there is some ambiguity about whether 0 is to be
onsidered a

natural number; we in
lude it and use the term to mean non-negative integers.

To represent a natural number we

**rst write it in binary. So if we wish to represent the
**

de
imal number 25 on a
omputer, we

and even whi h of the apa itors stores the least signi. we would typi ally dedi ate one apa itor somewhere in our omputer. we would have to designate some 5 apa itors. Now ea h binary digit. low.rst write it as 11001 in binary. If we want to store a 5 bit number. To represent a bit. is represented separately. low. and put a low or high voltage on that apa itor depending upon whether we want to represent a 0 or 1 respe tively. and high voltages on them. or bit of the binary number. and store respe tively high. For ea h bit there are only two possibilities: 0 or 1. It is of ourse our reponsibility to keep tra k of where we store ea h number. high. su h as 11001.

ant bit. se ond least signi.

and so on. and a high urrent might represent 1 (again with some agreed upon values for what high and low means). many simple things are not understood. low voltage might mean 0 volts. how pre isely do rain drops form.7 volts. we understand enough (through the hard work of several s ientists) to make predi tions with some on. It is also possible to designate wires in our omputers for this purpose: a low urrent in the wires might represent 0. ant bit. In fa t. High voltage might mean 0. Using voltages on apa itors to represent numbers is not the only way.g. However. e. Magnetization might also be used: magnetization in one dire tion might 1 This is not to say that all physi al phenomenon related to the weather are well understood.

All this is of ourse well outside the s ope of this book.den e. .

0 volts represent a 0 and 0. for instan e. the task of pro essing numbers an be expressed as an ele tri al engineering question: given a ertain on. Be ause of su h onsiderations. this idea ould be implemented. 0. a re e tive region might represent a 1. in another might mean 1. This is ommon for storing data on magneti dis s (or tapes.35 as 1.2 but be ause of some ele tri al noise or some ir uit imperfe tion it only got raised to 0. it turns out that using the binary representation is the most onvenient.1 This would then hange the value that we stored! If this number represents a letter.2 to represent 2. do we not use 0 volts to represent 0. and so on.35 will be interpreted as 0 and any voltage above 0. Do not distribute 29 mean 0. But in the real world. On the other hand.1 to represent 1. In an ideal world.7 volts represent a 1. a non re e tive region a 0. You may wonder whether using bits to represent numbers is the only possible way. 0. This in ee t means: any voltage below 0. On e we have found a way to represent numbers using voltages or urrents. 0. This turns out to be unlikely for the te hnology we have for building su h ir uits. An opti al CD is divided into a large number of su h regions. there are imperfe tions: it is possible that we intended to raise the voltage of a wire to 0. Why. ea h of whi h an be used to store a bit. then it would hange a \p" to \q" or something like that { whi h would be quite una eptable. On opti al dis s. long ago). Abhiram Ranade.3 to represent 3. Now to ause a misinterpretation we would need to have noise as large as 0. suppose we instead have 0. 2011.35 volts.

produ e another on.guration of voltages or urrents.

say the memory. we dis uss these parts and their operation in greater detail. We will use this de. 2. and a ontrol unit. As mentioned earlier. 2 2. The parts mentioned above are onne ted together by a network. a bit is typi ally stored using a apa itor. Groups of 8 bits are alled bytes. and a group of 4 bytes onstitutes a word. This is how data an be said to ow between parts of the omputer.2. It is possible to ommand any part. to pla e data onto the wires onstituting the network. input devi es su h as the keyboard. an arithmeti logi unit (ALU). Other omponents onne ted to the wires.3 Memory The basi unit of memory is a bit. an be instru ted to read this pattern from the wires. In the following se tions. high voltage a ross it denoting the value 1 and low voltage denoting the value 0. output devi es su h as a monitor.guration of voltages or urrents. Thus the same pattern of voltages that was in the memory appears on the wires.1 Organization of a omputer It is ustomary to think of a omputer as onsisting of several parts. a memory. say the ALU. The ontrol unit and the ALU are together often alled the entral pro essing unit (CPU).

nition of a word. even though it is not as universally as a epted as the de.

unusual input devi es su h as temperature or illumination sensors or output devi es that ontrol beepers or even motors might also be present.nitions of bits and bytes. As we remarked earlier. and the term double-word for two onse utive words of memory. The term half-word is often used to refer to the two bytes onstituting ea h half of a word. 2 .

The data port is a set of 32 wires ( orresponding the size of a word) onne ting the ir uitry of the memory and the rest of the world. word-oriented organization for this memory. The memory ir uits allow us to perform two operations on the memory: write a word into it. an address port. We begin by pla ing the number y on the address bus. It is useful to assume that the bytes in the memory are arranged in a sequen e. Suppose that a omputer has 2 bytes of memory. where 0 y < 2 . The ontrol line is a single wire. Abhiram Ranade. Do not distribute 30 The memory an be thought of as onsisting of a sequen e of bytes (whi h in turn is a sequen e of 8 bits). The memory onne ts to the rest of the omputer using a data port. The address port is another su h set of 30 wires (as many as the logarithm to base 2 of the number of bytes in the memory). Here is a possible. and read a word from it. By this we mean that we onvert y to binary. and pla e a low/high voltage on the ith wire of the address bus as per the ith least signi. and a ontrol line. The main memory in a present day omputer an be several gigabytes where a gigabyte is 2 bytes. 2011. The yth byte in the sequen e is said to have the address y. We an write a number x into the word starting at address y by using the following pro edure.

y + 1. in bytes with addresses y. y + 3. We pla e the number x.g. We again hold this pattern for the duration of the y le time. Similarly for bytes. the phrases \word with address y" or \word at y" or sometimes even just \word y" is used to mean the word starting at address y. y +2. The value on the data wires an then be sensed by the inter onne ting ir uitry and opied to other parts. we are assured that the value x is deposited in the word starting at address y.1 Storing text We mentioned earlier that text is represented using the ASCII ode: ea h hara ter is given a numeri al ode whi h an be stored on the omputer. or double-words. then z appears on the data bus.e. y +3 treated as a single word.e. ant bit of y. and at the end of the y le time. on the data bus. though). half-words. and a 1 (high voltage) on the ontrol line. i. y + 2. we pla e the number y on the address bus. 30 30 30 3 2. the arithmeti logi unit. the word starting from address y). onsisting of 32 bits. By the way.e. y +1. This auses the ir uitry in the memory to do its work.3. and hen e the ode assigned to any hara ter an . We pla e a 0 (i. If the value z was present in bytes y. e. To read the ontent of the word at y (i. a low voltage) on the ontrol line. All these voltages are held steady for a duration alled the y le time of the memory. Ea h ode is an integer in the range 0 through 255 (not all integers orrespond to visible hara ters.

this is perhaps the reason the byte was de.t in 1 byte. Indeed.

then these do not overlap with ea h other. it is required that be a multiple of 4. Most ommonly. This has some advantages. but we will not worry about this. If all words start on addresses that are multiples of 4.ned to be made up of 8 bits. 3 y . text is represented on a omputer by pla ing the ASCII odes of onse utive letters in onse utive bytes in memory. In any ase.

Do not distribute 2. we usually do not ask for an arbitrary number of bits. when allo ating memory to store a number. or a word.3. or a half-word. To store a number. as will be seen in the following hapters.2 Storing natural numbers We have already dis ussed that natural numbers are stored in binary. we must . 31 Abhiram Ranade. or a double-word. However. and wish to store 25 in it. If we asked for 32 bits. we need to allo ate at least as many bits of memory as there are bits in the number. 2011. it is ustomary to ask for a byte. or a word of memory.

2. In this. if n bits are used in total. while a high voltage indi ates that the stored number is negative. as: 00000000000000000000000000011001 This pattern of bits would then have to be stored in the hosen word. how would we represent the integer -25? The simplest representation is the so alled sign-magnitude representation.3 Storing integers Integers are dierent from natural numbers in that they an be negative as well. We might use the bit in the most signi. We ould de ide that a low voltage on the apa itor indi ates that the stored number is positive.rst write 25 using 32 bits. This throws a new hallenge: for example.3. one of these is designated as a sign bit. So in addition to the apa itors we dedi ate for storing the magnitude. we will also dedi ate one apa itor for storing the sign.

so the representation for -25 using the 32 apa itors would be: 10000000000000000000000000011001 A more ommonly used representation is the so alled 2's omplement representation. The n bit 2s omplement representation is de. ant position as the sign bit.

Thus. voltages.3. velo ities of parti les. For example. In this the integer x is represented by the binary number x if 0 x 2n 1. In the s ienti. in 32 bit 2's omplement representation.ned as follows. -25 would be represented by the bit pattern: 11111111111111111111111111100111 1 1 2. temperatures and so on in general need not take only integral values. and by the binary number 2n x if 2n x < 0.4 Storing real numbers Mu h omputing needs to be done with real numbers.

world su h quantities are typi ally written using the so alled s ienti.

where the signi. in the form: f 10q . notation.

or Avogadro's number is 6:022 10 . How should we store Avogadro's number on a omputer? First of ourse. this is easily done: it is 1:11111110001010101111111 2 31 23 1001110 . For example the mass of an ele tron is 9:109382 10 kilograms. we must represent it in binary. and f typi ally has a magnitude between 1 and 10. and the exponent q is a positive or negative integer.

Abhiram Ranade, 2011. Do not distribute

32

**Note that this is approximate, and
orre
t only to 3 de
imal digits. But then, 6:022 10
**

was only
orre
t to 3 digits anyway. The exponent 1001110 in de
imal is 78. Thus the

number when written out fully will have 78 bits. We
ould use 78 bits memory to store

the number, however, it seems unne
essary, espe
ially sin
e many of those 78 bits will be

0s anyway. A better alternative, is to store ea
h number in two parts: one part being the

signi

**and, and the other being the exponent.
**

For example, we
ould use 8 bits to store the exponent, and 24 bits to store the signi

and,

so that a number is neatly

**tted into a single word! This turns out to be essentially the
**

method of
hoi
e on modern
omputers. You might ask why use an 8-24 split of the 32 bits

and why not 10-22? The answer to this is experien
e: for many
al
ulations it appears that

24 bits of pre
ision in the signi

**and is adequate, while the exponent size of 8 bits is also
**

needed. There are s
hemes that use a double word as well and the split here is 11-53, again

based on experien
e.

Note that the signi

**and as well as the exponent
an be both positive or negative. One
**

simple way to deal with this is to use a sign-magnitude representation, i.e. dedi
ate one bit

from ea
h

eld for the sign. Note that we dont need to expli
itly store the de
imal point (or

we should say, binary point!) { it is always after the

rst bit of the signi.

and. Assuming that the exponent is stored in the more signi.

11111111000101010111111 Two points to be noted: (a) we have put ommas after the sign bit of the exponent. 0. and the sign bit of the signi. Avogadro's number would then be stored as: 0. 1001110. the exponent itself. ant part or the word.

only so it is easy to read. There are no ommas in memory. and. (b) Only the most signi.

ant 23 bits of the signi.

This requires throwing out less signi. and are taken.

but you might even have to pad the signi. ant bits (what happened in this example).

e. 1. The memory simply holds sequen es of 0s and 1s. It is mu h more ompli ated. So if you de ide to use it for storing real numbers (or other kinds of 32 . the representation would be 0. 0000011. a natural number. The same word of memory an be used to store 4 ASCII hara ters. 110001010000000000000000 Again the ommas are added only for ease of reading. 32 bits. or a oating point number. 23 3 2. This is -1100. it is upto us to remember what type of data we have stored. Another point to be noted is that a word of memory. some of whi h we will use later. i. onsider representing 12:3125. des ribed in detail in Appendix E. an integer. i. As another example. and thereby orre tly interpret the bit sequen e. but has more features. an represent 2 distin t bit patterns. 1:1000101 2 . all data. be it text or be it numbers.0101 in binary. Noting that our number is negative and our exponent is positive.5 Remarks It is important to note that when stored in memory.e. is merely a olle tion of bits.3. The exa t format in whi h real numbers are represented on modern omputer hardware and in C++ is the IEEE Floating Point Standard. and with 0s if it happens to be smaller than 23 bits.

and orrespondingly redu e the pre ision at whi h ea h number is expressed. it an store at most 2 distin t numbers. we in rease the range of magnitudes we an store. But there are in. When we de ide to give more spa e to the exponent. But the number of numbers that an be represented remains at most 2 as before. 2011. Do not distribute 33 numbers). Abhiram Ranade.

nitely many natural numbers or integers or real numbers! So using just one word of memory (or indeed any .

our representation given above annot represent natural numbers bigger than or equal to 2 . there will always be numbers whi h we annot represent. In fa t. For example. Our integer and real number representations also have similar limitations.xed number of words). the real number representation is further limited be ause it is approximate: all numbers are represented only to a .

what is its representation as a real number (exponent and signi. But if you feel that for some omputation you read mu h larger numbers or numbers with mu h higher pre ision. omparisons. multipli ation. e. By and large these limitations are not serious. This must be done by performing a sequen e of arithmeti operations.nite pre ision. 32 32 32 2. We will see this later.4 Arithmeti Logi Unit The arithmeti logi unit (ALU) has ir uits using whi h it is possible to perform arithmeti operations. division. The ALU will also have ir uits using whi h we an onvert between dierent number types. addition. for numbers in all formats des ribed earlier. subtra tion.g.10. and real numbers. as is hinted at in Exer ise 5. you an implement them yourself. integers. given a number represented as an integer. natural numbers. e.g. Note that a omputer annot dire tly ompute standard fun tions su h as say the sine or osine.

The answer to this question an be either \Yes" or \No". How exa tly we an use this information will be ome lear in Se tion 2. it will have various ontrol inputs. And indeed a lot of lever design is needed. the sum annot be stored in a single word. Su h values. and we want to know what the se ond of those hara ters is. For simpli ity we will assume n = 32. Ea h ontrol input an be thought of as a single wire. The inputs and the outputs will ea h onsist of some number n of wires. whi h if set to 1 will ause the ALU to perform the orresponding fun tion (e. 32 . 0 respe tively. In this ase there is said to have been an over ow. For the des ription to ome later. There will be auxiliary outputs whi h will indi ate whether the last operation produ ed a zero result or a positive or negative result and so on. The ALU an dete t an over ow and remember it. our ALU operates on 32 bit data.g. false are ommonly represented by 1. True. we must extra t just the se ond byte out of the word. The ALU also has ir uits to remember information su h as \was a positive value omputed in the last arithmeti operation?". In addition. or equivalently the values \True" or \False" are said to be Logi al Values.g. we will onsider the ALU to have 2 inputs. and a single output. In that ase. add the two numbers on the inputs assuming they are real numbers). When you add two natural numbers. and it is a s ien e by itself.e. the sum might be be ome 2 or larger. input1 and input2. e. The set of ir uits that seem to be needed might seem bewildering. Hen e the in lusion of the term Logi in the name of this unit. i. when a word ontaining 4 hara ters is loaded.6. and)? Also there will be ir uits whi h an extra t bytes or bits out of a word.

and more apabilities will be needed even for a dumb terminal. say 1024 rows and 1024 olumns. are of ourse mu h more omplex. To display an image. blue omponents at ea h pixel. A reasonable orresponden e is used to relate the pixels and addresses in memory: the olour information for the pixel (i. it might be enough to merely de ide whether the pixel is to appear white or bla k. Asso iated with ea h pixel.e. If we have 24 bits of memory per pixel.5 Input-Output Devi es The simplest input devi e is a keyboard. in whi h we expe t to store data. You probably know that a omputer s reen is made up of pixels whi h are arranged in a grid. So a single bit of memory is enough. When the ir uitry of the s reen needs to display the olour at pixel (i. ea h ell of the memory onsisting of 24 bits. the pixel in row i and olumn j (with 0 i. For a simple bla k and white display. there is a ertain amount of memory. however. In olour displays we need to simultaneously store the red. 34 Abhiram Ranade. the orresponding ode number is sent to the omputer. and so presumably even more bits are needed. The manner in whi h you display a symbol is simple: the omputer sends the ode number asso iated with the symbol to the s reen. However. So to the omputer. j ) i. 2011. This memory should not be onfused with the main memory of the omputer dis ussed earlier. j < 1024) is stored in address 1024i + j of the memory. and the terminal ontains ir uitry whi h auses the orresponding symbol to be displayed at the urrent ursor position. Devi es su h as disks an also be thought of as storing data at ertain addresses. Do not distribute 2. Modern s reens. The amount of memory depends on the sophisti ation of the display. When the omputer needs to hange the image. the addresses no longer refer to spe i. su h as the one you would need to display our turtle. there must be a way for the omputer to lear the s reen ompletely. For example. this is a very simplisti des ription. then be ause there are 1024 1024 = 2 pixels. whi h determines what olour is shown in that pixel. You may also have variations of gray: k bits of memory will be able to store numbers between 0 and 2k 1 and hen e that many gray levels. j ) it pi ks up the olour information from address 1024i + j of the memory. all we need to do is to store appropriate values in the memory asso iated with ea h pixel in the s reen. Indeed high quality olour displays might use as mu h as 24 bits of memory for ea h pixel. it merely hanges the data in the memory. we will need a memory with addresses between 0 and 2 1. When a key is pressed. The simplest output devi e ould be what used to be alled a \dumb" terminal: a s reen on whi h you an merely display essentially the same symbols that you an type from your keyboard. A ode number is assigned for ea h key on the keyboard. the s reen appears very mu h like another memory. green.

apa itors in the ir uitry. but spe i.

in the required sequen e.6 The ontrol unit As the name implies. 20 20 2. A De ode Unit (DU). and an Instru tion-Fet h Unit (IFU). lo ations on the magneti surfa e. The ontrol unit has two parts. The DU onne ts to the other parts of the omputer and ommands them to do dierent a tions. In keeping with the idea that everything . How does the DU de ide what ommands to issue to the other units? This depends upon the instru tions supplied to the DU by the IFU. the ontrol unit ontrols the other parts of a omputer and auses them to perform the required work.

After fet hing that instru tion and sending it to the DU. However. the IFU is initially told the address from whi h the instru tion needs to be fet hed. we present some examples of what the instru tions might look like.g. instru tions are stored in the same memory that is used for storing the data. In any ase. it turns out that the instru tions are also expressed using numbers. the IFU then fet hes the instru tion stored at the next address. Abhiram Ranade.g. on most omputers. Do not distribute 35 on a omputer is numeri al. What we des ribe is very simplisti and is meant only to help understand the overall me hanism. memory. 2011. All this is mu h more elaborate on real omputers. send a value from memory to the ALU. For simpli ity we will assume that the instru tion sent to the DU by the IFU onsists of two words. The ir uits in the DU interpret the numbers it re eives from the IFU and de ides whi h part (e. You will of ourse want to know how the IFU knows what numbers to send to the DU. by default. It merely reads them from the memory! For simpli ity. and so on. ALU) should be ommanded to do what (e. It is ustomary to all the . To make these ideas more vivid. you may assume that the IFU has its own private memory in whi h instru tions are stored. or perform addition in the ALU).

and display their sum on the s reen. 4008. The instru tion for this (assuming the numbers are integers) is 2. 0. 4004. . 99. 0. 0. the operand. and the se ond word. Say we de ide to use the word starting at 4004 to store the se ond integer.4008. 4008. and the omputer would then stop. 2. so the instru tion we spe ify is 42. So we an put the sequen e of numbers 31. 4000. 31. 4008.2 shows some possible instru tions that we ould have in a omputer.4004. What instru tions would we need to send to the DU? We would begin with the ommand for reading an integer from the keyboard: this has operation ode 31. Finally we have to print the result on the s reen. Then we would need to ommand the ALU to add. 4000. The operand is typi ally interpreted as a memory address by the DU. The operation odes for this are 0 and 1 respe tively.4000 and 1. Noti e that a word takes up 4 bytes.0. 4004. and so we should not use the addresses from 4000 through 4003 for any other purpose. We would then need to move the numbers to the inputs of the ALU. 0 into the memory.rst word the operation ode. So we would need instru tions 0. 1. 10. Printing on the s reen has operation ode 42. Note that the sequen e of numbers des ribed above ould really be alled a program. Figure 2. The instru tion for doing this would be given by the numbers 31. say address 4008 (by whi h we mean the word starting at address 4008). 42. Then we would a omplish what we wanted: read two numbers and print their sum. Finally we stop the omputer using the instru tion 99. After this the result must be pla ed somewhere. and instru t the IFU to fet h from 100. We will see later how the C++ programs that you saw in Chapter 1 are related to ma hine language programs. So we would have to exe ute an instru tion whi h would be represented by the pair of numbers 31. Let us arbitrarily de ide to store the integer in the word starting at address 4000. Suppose now that we wish to read two integers from the keyboard. In fa t it is ustomary to all su h a sequen e a ma hine language program. say starting at address 100. This is done by the instru tion 10. 4000. 4004.

42 x Send the data stored in address x to the s reen. ex ept that 14 is for integers and 15 for oating point numbers. Store that value in address x of the memory. 14. the hara ter 'a' would be printed. 10 0 Command the ALU to perform the addition of the values in its inputs. When a key is pressed. Figure 2. Abhiram Ranade. the keyboard will send its ASCII value. 31 x Wait for an integer to be typed on the keyboard. Store the result in ALU output. Code Operand Ee t of the instru tion 0 x Move data from address x of memory to input 1 of ALU. Instru t the s reen to interprete data as an integer. 99 0 Stop. Store the result in ALU output. treating them as oating point numbers. 12 0 Command the ALU to perform the addition of the values in its inputs.15 0 Same as above. 41 x Send the data stored in address x to the s reen. 13 0 Command the ALU to treat the inputs as natural numbers and subtra t input 2 from input 1. Store the result in ALU output. So if the data was 97. the hara ter \97" would be printed. 1 x Move data from address x of memory to input 2 of ALU. and store the result in ALU output. So if the data was 97. 2011. treating them as natural numbers. 11 0 Command the ALU to perform the addition of the values in its inputs. and print the orresponding hara ter. treating them as integers. and print it. Instru t the s reen to interprete data as an ASCII ode. 2 x Move data from ALU output to address x of memory. 30 x Wait for a key to be pressed on the keyboard. Do not distribute Op.2: Some possible instru tions and their ee ts 36 . Re eive the value of the integer into address x of the memory.

Normally. Suppose now that the instru tion urrently being exe uted. Code Operand Ee t of the instru tion 110 x Instru t the DU to fet h subsequent instru tions from address x. so saying that the instru tion was taken from address really means that it omes from bytes + 7 of the memory. It reads two numbers from the keyboard. : : : . Figure 2. x . we might say that ontrol ows through that sequen e of instru tions or addresses. For example. the ontrol unit exe utes instru tions in the order in whi h they are stored in the program memory. then the ontrol would ontinue with exe uting the next instru tion. Then it is ustomary to say that the ontrol (unit) is at that instru tion. the instru tion following that would ome from address x + 8 and so on. 114 x Instru t the DU to fet h subsequent instru tions from address x if there was an over ow in the last ALU operation. Figure 2. But if the urrent instru tion is 110. 2011. start fet hing and exe uting instru tions from a dierent address in memory. and suppose the instru tion was taken from address x of the memory. 4 x x.1 Control Flow Suppose that the IFU is urrently sending a ertain instru tion to the DU. whi h ame from address y was 111. then the next instru tion would instead ome from address x.6. the one from address y + 8. or at the address x. i.e. Note that similar phrases are also used in onne tion with C++ programs: we will say that the ontrol is at a given statement of the program and so on. If the last arithmeti operation produ ed a 0 value. However. Figure 2. suppose that urrently the instru tion being exe uted was from address y. in other words. 112 x Instru t the DU to fet h subsequent instru tions from address x if the last result omputed by the ALU was positive. i. x. Then the next instru tion would normally ome from address y + 8. x.e. Alternatively.4 gives an example of a program whi h uses jump instru tions. Unless the instru tion at x is itself a jump instru tion. It is also possible to jump onditionally. If the last arithmeti result was not 0. 113 x Instru t the DU to fet h subsequent instru tions from address x if the last result omputed by the ALU was negative. The sequen es of addresses of the instru tions exe uted by the ontrol unit is said to onstitute the path of ontrol ow. Do not distribute Op. then the ontrol would jump to address x. 37 Abhiram Ranade. most omputers also have instru tions that ause the ontrol to jump to a dierent lo ation. and prints the se ond number as many times as the value of 4 Note that we have said that an instru tion onsists of 2 words.3 shows examples of jump instru tions. sin e we know that ea h instru tion is 8 bytes long. 111 x Instru t the DU to fet h subsequent instru tions from address x if the last result omputed by the ALU was 0.3: Jump instru tions 2.

4: Program to print many times the . Print data from 4000 to s reen. Move data from 4004 to input 1 of ALU. Move data from 196 to input 2 of ALU. Stop exe ution. Read into address 4004. Abhiram Ranade. Subtra t (integers) and move result to ALU output. If last result was positive jump to address 216. Do not distribute Address 196 200 204 208 212 216 220 224 228 232 236 240 244 248 252 256 260 264 268 Data 1 31 4000 31 4004 0 4004 1 196 42 4000 13 0 2 4004 112 216 99 0 38 Explanation Read into address 4000. Figure 2. 2011. Move ALU output to address 4004.

The program does assume that the .rst number.

rst number is positive.2 Some tri ky instru tions Before we on lude this se tion.6.5 we introdu e a few tri ky instru tions whi h we will talk about in later hapters. 2. in Figure 2. but also see the exer ises. The .

We do not think about what instru tion odes to use. look up the omputer manual and determine the operation odes needed to perform the a tions you wanted. Indeed. but the address of the address. store.rst 3 use the operand not as the address. and jump respe tively. Then these numbers would have to be loaded into the omputer memory. today. you had to de ide where in memory you would store your data.7 High level programming languages When the earliest omputers were built. we use familiar mathemati al . they ould be used only by writing ma hine language programs. programs an be written in the style seen in Chapter 1. Instead. and then you ould exe ute the program. and then write out the sequen e of numbers that would onstitute the ma hine language program. this whole pro ess is very tiring and error prone. Fortunately. Hen e these instru tions are said to be indire t load. As you an see. nor the address in memory where to store the number of sides of the polygon we wish to draw. 2.

the ni e looking programs we write must . and move the data in the output of the ALU to address y. Start fet hing the instru tions from address y.5: Some tri ky instru tions formulae to denote operations we want performed. The omputer. Use y as an address. Store z + 1 into address x. and move the data in address y to input 1 of ALU. Abhiram Ranade. Use y as an address. and does not understand mathemati al notation or the names we give to parts of memory. Code Operand Ee t of the instru tion 120 x Let y be the natural number stored in address x. 123 x Suppose z is the address from whi h the IFU fet hed the urrent instru tion. Do not distribute 39 Op. Figure 2. So how does our ni e looking program a tually exe ute on a omputer? Clearly. really only \understands" instru tion odes and memory addresses. of ourse. 2011. We give names to regions of memory and store data in them by referring to those names. 122 x Let y be the natural number stored in address x. 121 x Let y be the natural number stored in address x.

Here is a C++ program equivalent to the ma hine language program we des ribed in the previous se tion. num3. whi h fortunately has been written by someone already! The program s++ that you used in the last hapter is a C++ ompiler. whi h takes a C++ program (e.out) whi h an be dire tly exe uted. main_program{ int num1. This is done by a program alled a ompiler. num3 = num1 + num2.g. a. that the omputer an understand.rst be translated into the language of instru tion odes et . in >> num2. out << num3. num2. pp) and generates the ma hine language program (e. } Can you see the orresponden e? The . square.g. in >> num1.

and it de.3.1.rst statement is as dis ussed in Se tion 1.

is equivalent to exe uting the instru tions 0. num2. The fourth statement. do the work done by the instru tions 31. 4004. the .4004. num3.nes the variables num1.4000 followed by 1.4004 followed by 11.4008. num3 = num1 + num2.4000 and 31. 4008 respe tively. Finally. These variables play the role of lo ations 4000. The statements in >> num1. and in >> num2.

4008.fth statement is equivalent to the instru tion 42. .

0. 4000. 4004. But the ompiler will use some three lo ations. Of ourse. 42. why would you are whi h lo ations are used? By the way. 2011. 99. 1. 4008. 4004. 4008 to store the data. 4000. and generate the instru tion sequen e. 4004. an you tell why the ompiler de ided to use the instru tion ode 11 and not the odes 10 or 12? The ompiler an make this de ision be ause of the . 31. there is nothing in the C++ program whi h says whi h lo ations to use. 11. the ompiler may not use lo ations 4000. Abhiram Ranade. 0 des ribed earlier. su h as the sequen e 31. But so long as the sequen e does what you want. Do not distribute 40 A C++ ompiler will take a program su h as the one above and generate the sequen e of instru tions equivalent to it. 4008.

rst statement. We now explain this.g. However.8 Boot Loader We made a rypti remark earlier about how the IFU an be \asked to start fet hing instru tions from lo ation 100". whi h says that the numbers are integers (and not natural numbers or oating point numbers. 2. whi h would require the odes 10 or 12 respe tively to be used). i. Most of the memory used in modern omputers is said to be volatile.e. the memories of most omputers ontains a non-volatile part. the data stored in it is destroyed when the omputer is swit hed o. say the data in addresses 0 to 100 is . e.

whi h loads a program from the keyboard. This is of ourse. they also have a boot loader whi h runs. but you do have all the instru tions you need to be able to do it. e. The operating system then ommuni ates with the user and then runs the programs that the user wants. or Ma OS or whatever. In the exer ises. the boot loader starts exe uting the just loaded program. you are asked to write a boot loader program. when the omputer is swit hed on. Linux. is only apable of loading the program that the omputer is really meant to exe ute. or Windows.9 Con luding Remarks The . Typi ally. it starts exe uting a program stored in this non-volatile memory. When you swit h on modern omputers.g.xed by the manufa turer and this data stays un hanged no matter how many times the omputer is swit hed on and o. and then exe utes it. often alled the boot loader program. Further. After loading the real program. a diÆ ult and tiring exer ise. this program. The boot loader loads and runs the operating system. But it all begins with a boot loader! 2.

rst important point made in this hapter is that for solving any problem. you .

and these programs are sequen es of instru tions. . The se ond important point was that numbers an be pro essed using appropriately designed ir uits. ea h of whi h is also represented using numbers! Finally. and it is hoped that you will ask yourself how those might get translated to ma hine ode. In the following hapters we will see more C++ statements. Su h ir uits an be ontrolled using programs.rst need to express it as a problem on numbers. we dis ussed the orresponden e between ma hine language and C++.

Show that we an perform multipli ation of two numbers using add operations and jump operations. and that real hardware is mu h more elaborate. and 2 pixels thi k.10 Exer ises 1.4. In whi h s reen memory lo ations would you store 1s? 4. q separately. that the des ription of omputer hardware in this hapter was very simple-minded. i. How many dierent numbers are represented in the n bit 2's omplement representation? Compare this to the sign bit representation dis ussed in the text. 2. One way to store a rational number p=q is to store p. Is there a bit in the 2s omplement representation whi h an be onsidered to be a sign bit. in whi h we store have 1 bit for storing the sign. Would this be better than performing the division and then storing the resulting real number to a . For simpli ity.e. Do not distribute 41 It should be noted. Suppose a ertain omputer does not have an instru tion to multiply. 2. Suppose the display will show a pixel white if you store a 1 at the orresponding memory lo ation. and the remaining n 1 bits for storing the magnitude. 6. 3. however. Suppose the \+" is 100 pixels tall and wide. 2011. Write a C++ program equivalent to the ma hine language program of Figure 2. Abhiram Ranade. 5. Suppose you want to draw a \+" symbol at the enter of a 1024 1024 display. it is 0 for positive numbers and 1 for negative numbers? Having su h a bit is onvenient be ause we an qui kly tell whether the number is positive or negative. your program should simply add the multipli and to itself as many times as the multiplier.

The .xed number of bits? What do you think are the tradeos? 7. Write a boot loader program. It whould wait and read two integers n and s from the keyboard.

: : : . the so alled tri ky instru tions.rst integer n will give the length (number of words) of the program that will be supplied by the user subsequently. over the keyboard. s + 1. You may need to use some of the instru tions we dis ussed last. Finally the boot loader should jump to address s. s + n 1. The boot loader should then read the n additional words from the keyboard and store them into addresses s. The se ond integer s gives the starting address where this program is to be loaded. .

This will determine how numbers will be represented when stored. performing arithmeti or other operations on them. Table 3. This information. allo ate the memory. We see some of these at the end. i. When you ask for a variable to be reated. Text pro essing turns out to be a minor variation of numeri pro essing. In this hapter. you need to spe ify the type of data you want to store in the variable. If you want to store numbers at high pre ision. whether the numbers you wish to store are natural numbers. the exa t rules are dis ussed in Se tion 3. we will build up on that and state everything more formally and more generally.3. and give it a name.1. you need a bigger region of memory. they are onsidered at length in Se tion 13. Clearly. Logi al data is also represented numeri ally. the variable nsides of Se tion 1. and writing them onto the s reen. are together said to onstitute the data-type of the variable.1 and Se tion 5. and the amount of of pre ision. The name is to be used to refer to the variable in the rest of the program. Using the repeat statement and what we learn in this hapter we will be able to write some interesting programs. and real numbers are typi ally represented in distin t ways.Chapter 3 Numbers In this hapter we will see C++ statements for pro essing numbers.1 shows the data types that 42 . C++ allows you to reate a variable.6 respe tively. storing them in memory.e. or real. As we saw in the previous hapter.1 Variables and data types A region of memory allo ated for holding a single pie e of data (for now a single number). As mentioned in Chapter 2. and also of the values stored in the variable. You have already seen one example of reating a variable.1. By this we mean details su h as whether you want to store natural numbers or integers or real numbers. We onsider these topi s brie y. these a tions are at the heart of any program. We will see more examples shortly. integers. textual data is also represented numeri ally on a omputer: ea h hara ter is represented by its numeri al ASCII ode. We have already seen examples of these a tions in the programs in Chapter 1. it is ne essary to indi ate how mu h pre ision you need. integers. natural numbers. 3. You have onsiderable freedom in hoosing the names to give to variables. In addition.3. By \pro essing numbers" we mean a tions su h as reading numbers from the keyboard. is alled a variable.

Storing high pre ision and very high range real numbers. Storing long integers. About 18 digits 12 of pre ision. Storing standard size integers. .1: Fundamental data types of C++ Use Storing hara ters or small integers. Magnitude in the range 3:3621 10 to 1:18973 10 38 308 4932 38 308 4932 Table 3. Magnitude in the range 1:17549 10 to 3:4028 10 double Positive or negative. Do not distribute Data type Possible values Size in bytes (Indi ative) (Indi ative) signed har -128 to 127 1 unsigned har 0 to 255 signed short -32768 to 32767 2 unsigned short 0 to 65535 signed int -2147483648 to 2147483647 4 unsigned int 0 to 4294967295 signed long -2147483648 to 2147483647 4 unsigned long 0 to 4294967295 bool false (0) or true (1) 1 float Positive or negative. Storing high pre ision and high range real numbers. Storing real numbers. 43 Abhiram Ranade. Storing logi al values. Storing medium size integers. About 15 digits 8 of pre ision. Magnitude in the range 2:22507 10 to 1:7977 10 long double Positive or negative. About 7 digits 4 of pre ision. 2011.

Abhiram Ranade. Do not distribute 44 are prede. 2011.

In this. and we will say how to do this shortly. and you are required to hoose from these types. data-type must be a data-type sele ted from the . On e you de ide on the data type. you an reate a variable by writing the following in your program. data-type variable-name.ned in C++.

and variable-name a name hosen as per Se tion 3.1.1 does not mention the representation s heme to be used for this variable. As an example. Then to store it.rst olumn of Table 3. The phrase value of a variable is used to refer to the value stored in the variable. perhaps you would hoose unsigned int as your data type.1. So the stored telephone number (after it is stored. of size given in olumn 3 of the table. unsigned int telephone_number. and we will say how to do this) will be the value of the variable telephone number. suppose you know that a ertain number that you wish to store will be a non-negative integer. This would give you a variable onsisting of 4 bytes of memory whi h you ould refer to using the name telephone number in the rest of your program. with no more than 8 digits. and you would write the following line in your program. but from Se tion 2. When this statement is exe uted a region of ( ontiguous) memory will be allo ated. Then perhaps you might hoose telephone number as the name for your variable. Table 3.3. We .3. Say as an example that the number happens to be a telephone number.2 we know that the number would be stored using a 32 bit binary representation.

nally note that you an de.

by writing: data-type variable-name1. short. The exa t sizes are may vary from one ompiler to another. long to be in nonde reasing order.1 Remarks on Table 3. double. .1 It should be noted that the size shown for ea h data-type is only indi ative. int.. 3. Likewise. and a ordingly the possible values that the variables an take will also be dierent. The quali. variable-name2.1. long double are also expe ted to be non-de reasing.. variable-namek.ne several variables in a single statement if they have the same type. The C++ language standard only requires that the sizes of har. the sizes of float.

int. long default to signed. By themselves. The default for har may vary from one ompiler to another.ers signed and unsigned may be omitted. A pie e of terminology: the . short. the types.

har behaves somewhat dierently when it omes to reading data into it (Se tion 3.1.1 are said to be integral types. 3. However. then storing them in har variables is a . integer arithmeti an be done on har data just like the other integer types.rst 9 types in Table 3. For this use. and the last 3.1. floating types.6) and printing it (Se tion 3.7). So if your programs deals with a large number of integers ea h having a very small range. as you will see.2 Types har and bool The har type is most ommonly used for storing text.1.

as will be seen in Se tion 5.ne idea. The type bool is primarily used to store logi al values. .

Abhiram Ranade.3 Identi.1. 2011. Do not distribute 45 3.

ers The te hni al term for a name in C++ is identi.

Identi.er.

ers an be used for naming variables. An identi. but also other entities as we will see later.

digits and the unders ore hara ter \ ". Identi.er an onsist of letters.

ers annot start with a digit. hen e you annot have an identi.

er su h as 3rd ousin. It is also not onsidered good pra ti e to use identi.

Finally. The omplete list of reserved words is given in Appendix F. it is natural to name it velo ity. This way of forming names. in whi h several words are strung together. some words are reserved by C++ for its own use. it is not allowed to be used as a variable name be ause it will be onfusing. and in whi h the .ers starting with an unders ore for naming ordinary variables. so mathmarks is onsidered to be a dierent name from MathMarks. For example. It is ustomary to name a variable to indi ate the intended purpose of the variable. So if we want to store the velo ity in a variable. An important point is that ase is important in names. Noti e that the latter is easier to read. and these annot be used as variable names. int is a reserved word.

is said to be utilizing amel ase.rst letter of ea h word is apitalized. There are two kinds of CamelCase: UpperCamelCase in whi h the . the apital letters resemble the humps on the ba k of a amel. As you might guess. or CamelCase.

and lowerCamelCase. in whi h the .rst letters of all the words are apitalized.

rst letters of all but the .

unabbreviated. Thus if you have a variable whi h ontains the temperature. Or there is a lari. It is usually best to use omplete words. Sometimes the des ription that you want to asso iate with a variable name is very long. whi h expresses its use.rst word are apitalized. you should give it a des riptive name. If a variable is important in your program. or temp or tmprtre. it is more ustomary to use lowerCamelCase. For ordinary variables. thus it is suggested that you use mathMarks rather than MathMarks. it is better to give it the name temperature rather than t.

In su h ases. ation that the reader should be be aware of. it is good to add a omment explaining what you want immediately following the de.

1.5. as explained in Se tion 3. 3.nition.4 Initializing variables It is possible to optionally in lude an initial value along with the de.

This statement de.nition. q. So we may write: int p=10239.

of whi h the .nes 2 variables.

No initial value is spe i.rst one. is initialized to 10239. p.

.ed for q. i. whi h means that some unknown value will be present in it. in luding har and bool must be initialized by spe ifying an integer literal. the following additional ways of spe ifying integer literals are also provided in C++. it is to be interpreted literally as given. it is re ommended that you write initializations using these. The number \10239" as it appears in the ode above is said to onstitute an integer literal. e.e. All the integer types. For example the words false and true are literals whi h stand for the values 0 and 1. Any integer number with or without a sign onstitutes an integer literal.g. So for bool variables. However.

for the letter 'a' in the variable letter a. To initialize oating variables. but that would not make your intention lear. and that would denote the ASCII value of the hara ter. 97. For onvenien e in dealing with har data. or using an analogue of \s ienti. respe tively as 'nn' and 'nt'. rather than writing bool penIsDown=1. an be denoted by spe ial notation. any hara ter en losed in a pair of single quotes is an integer literal that represents the ASCII value of the en losed hara ter. Note that literals su h as 'nn' and 'a' really represent an integer value. whi h would mean the same thing but would be less suggestive. we need a way to spe ify real number literals. Thus you may write har letter_a = 'a'. 46 Abhiram Ranade. Chara ters su h as the newline. In general. or the tab. So we an in fa t write int q = 'a'. Do not distribute bool penIsDown=true. This would indeed store the ode. You ould also have written har letter a = 97. we may write a hara ter between a pair of single quotes. We an spe ify real number literals either by writing them out as de imal fra tions. 2011. This would ause 97 to be stored in the int variable q.

We simply write an E between the signi. notation".

6:022 10 . as 6. and and the exponent.022E23. The signi. Thus we would write Avogadro's number .

and as well as the exponent ould be spe i.

9:10938188 10 kg. This statement de. y=1.10938188E-31. of ourse.022E23. avogadro = 6. would be written as 9. Thus we may write: 1 23 31 float w. For example the mass of an ele tron. if needed.5.ed with a minus sign.

5 and 6:022 10 . 23 3. The variable w is not initialized.5 onst keyword Sometimes we wish to de.nes 3 variables. the se ond and third are respe tively initialized to 1.1.

ne identi.

. number of arbon atoms in 12 gm of arbon. and it will likely be onvenient to refer to it using the name Avogadro rather than typing the value everytime. Thus you might write onst float Avogardro = 6. Thus in this ase the ompiler will omplain if you later happen to make an assignment to it. In C++ you an use the keyword onst before the type to indi ate su h named onstants.g. e. 1 The number of mole ules in a mole of any substan e. On e a name is de lared onst. you annot hange it later.022 E 23.ers whose value we do not wish to hange. we might be needing Avogadro's number in our program. For example.

If pqr was of any of the oating types. First.5. so the . Do not distribute 3. the verti al tab 'nv'. Let us onsider an example. the statement ignores any whitespa e hara ters that you may type before you type in the value onsistent with the type of pqr. 2011. The exa t exe ution pro ess for the statement is a bit ompli ated. as dis ussed above. On e you start typing a value onsistent with the type of pqr. if any. and type 123 56 the spa es that you type at the beginning will be ignored. Suppose pqr has type int. In this ase the initial whitespa es that you type if any will be ignored. then a literal of that type would be expe ted.022e23 or 1. Any non-whitespa e value is onsidered appropriate for the type har. Simply put: when this statement is exe uted. the omputer will wait for us to type a value onsistent with the type of pqr. then the appearan e of a whitespa e hara ter serves as a delimiter.1. That value will then be pla ed in pqr. The 56 will used in a subsequent read statement. then if you exe ute the above statement. If pqr was of type bool you may only type 0 or 1.6 Reading data into a variable To read a value into a variable pqr we write in >> pqr. the formfeed hara ter 'nf' and the arriage return 'nr'. Thus we ould have typed in 6. you must type a newline either immediately following 123 or following 56. 47 Abhiram Ranade. the newline hara ter 'nn'. The term whitespa e is used to olle tively refer to the spa e hara ter ' '. the value 123 will be stored into pqr. Thus to pla e 123 into pqr in response to the statement above. Do not worry if you are unfamiliar with the last three hara ters in the list. in >> xyz. This is be ause the spa e following 123 will serve as a delimiter. Reading into a har variable You may not perhaps expe t what happens when you exe ute har xyz. Note further that the value you type will not be re eived by your program unless you type a newline after typing the value. the tab hara ter 'nt'.

rst su h value will be a epted. The ASCII value of the .

short. then xyz will be ome 49. Note that if you type 1.1. 3.7 Printing If you print a variable rst of type bool. writing . out << rst << endl. then xyz would get the value 97. This is be ause the ASCII value of the hara ter '1' is 49.rst non-whitespa e hara ter that you type will be pla ed into xyz. int or long. If you type the letter a.

A minus sign will be printed if the value is negative. 2011. The . Do not distribute 48 its value will be printed. Abhiram Ranade.

If you print a oating type variable.nal endl will ause a newline to follow. then C++ will print it in what it onsiders to be the best looking form: as a de imal fra tion or in the s ienti.

har xyz=97.1 mentions the indi ative sizes of the dierent data types. This will ause that hara ter whose ASCII value is in xyz to be printed. Thus in this ase the letter a will be printed. format.8 Exa t representational parameters Table 3. Printing a har variable Consider the following ode. 3. You an . out << xyz << endl.1. Following that a newline will be printed. be ause of the endl at the end of the statement.

nd the exa t number used by your ompiler by using the sizeof ommand in your program: out << sizeof(int) << endl. Say for float. you need to put the following line at the top of your . In order to use this fa ility. Or sizeof(double) and so on as you wish. the expression numeri limits<float>::max() gives the value of the largest oating point number that an be represented. You an also determine the largest or smallest (magnitude) representable numbers in the dierent types. Please do not worry about the ompli ated syntax of this expression. you an get the minimum/maximum values for all types. By using other types instead of float or by using min instead of max.

p. In a similar manner you an write expressions involving C++ variables. If you have an algebrai expression x y + p q .2 Arithmeti and assignment We an perform arithmeti on the values stored in variables in a very intuitive manner. and performing the operations as per the usual pre eden e rules. and the value of the expression is obtained by similarly onsidering the values of the variables and performing operations on them. y. with the same rules of operator pre eden e. almost like we write algebrai expressions. 3. q . The values resulting from evaluating an arithmeti expression an be stored into a variable by using an assignment statement. The notion of expressions is similar to that in Algebra.le (before or after other #in lude statements): #in lude <limits> We will see the exa t a tion of this line later. One dieren e is that often in Algebra the multipli ation . its value is obtained by onsidering the values of the variables x.

xy means x multiplied by y. 2011.-. whi h is *. whi h is higher than that of addition and subtra tion whi h have the same pre eden e. Some additional operators are also allowed. i. as will be dis ussed later. Abhiram Ranade. All the arithmeti operators +. In a C++ expression.*. we need to expli itly write the multipli ation operator. Do not distribute 49 operator is impli it. the one on the left is performed ./ are allowed.e. Among operations of the same pre eden e. Multipli ation and division have equal pre eden e.

However. This an be done using an assignment statement. The general form of an assignment is: variable = expression.r.y=3.rst. An expression auses a sequen e of arithmeti operations to be performed. it is your responsibility to ensure that the variable has been assigned a value earlier. int x=2.y. Note that when you use a variable in an expression. the omputed value is lost unless we do something with it. If we had C++ variables x. This will ause r to get the value of the spe i.p=4. 5-3+9 will mean 11. and a value to be omputed. write 5-(3+9) if we want this expression to evaluate to -7. Here is an example. and expression is an expression as des ribed above.g.q.g.q=5.p. One possibility is to store the omputed value in some variable. e. e. r = x*y + p*q. where variable is the name of a variable. We an use bra kets to enfor e the order we want. then the expression orresponding to the algebrai expression above would have to be written as x*y+p*q.

We ould also print out the value of the expression by writing out << x*y+p*q << endl.ed expression. say by initializing it at the time of de. Using the values given for the other variables. 26. Note that when you use a variable in an expression. the expression is simply 2*3+4*5. you must have assigned it a value already.e. i. Thus r will get the value 26.

the result will of ourse be unpredi table in general. asserts that the left hand side and right hand side are equal. In C++ however. Note that the operator = is used somewhat dierently in C++ than in mathemati s. or by reading a value into it from the keyboard. or in a previous assignment statement. After the assignment the values of the expressions on either side of the = operator are indeed equal if we onsider r on the left hand side to be a trivial expression. The rule des ribed above makes it perfe tly natural to write a statement su h as: p = p + 1. Note however. it is a ommand to evaluate the expression on the right and put the resulting value into the variable named on the left.nes it. In mathemati s a statement r = x*y + p*q. the variable will still ontain some value. be ause we require the left hand side to be a variable. that we annot write x*y + p*q = r. . If this is not done. If an unknown value is used in a omputation. only you dont know. into whi h the value of the expression on the right hand side must be stored.

% is the remainder or the modulo operator. Assuming p is as in the ode fragment given earlier. /.1 Modulo operator: % In C++. This operator has the same pre eden e as *. its value is 4. Do not distribute 50 This is meaningless in mathemati s. 2011. Abhiram Ranade. Thus the expression m % n evaluates to the remainder of m when divided by n. Note that a statement su h as p + 1 = p.2. 3.2. The .2 Subtleties The assignment statement is somewhat tri ky. is illegal { the left hand side p + 1 does not denote a variable. 3. in C++ however it just says: evaluate the expression on the right hand side and put the resulting value into the variable named on the left. Thus in this ase the value 4+1=5 would be put in p.

rst point on erns the oating point representations. where the signi. Both. float and double are impre ise representations.

and is orre t to a .

xed number of bits. So if an arithmeti operation ae ts less signi.

What is the value of w? Suppose for a moment that we pre isely al ulate the sum avogadro + y. float w.022E23 . avogadro=6. onsider the following ode. y=1. then the operation will have no ee t.5. This is be ause a float type variable an only stores signi. The sum will be 602200000000000000000001:5 We will have a problem when we try to store this into a float type variable. ant bits. w = avogadro + y. As an example.

or about 7 digits. we would treat everything beyond the most signi. ands of 24 bits. So in order to store.

ant 7 digits as 0. this an now . After the round o. If so we would get 602200000000000000000000 This loss of digits is alled round-o error.

it is worth knowing what exa tly happens.022E23.t in a float. C++ allows su h operations. This example shows the inherent problem in adding a very small float value to a very large float value. Net ee t of the addition: nothing! The variable w gets the value avogadro even though you assigned it the value avogadro + 1.5. Some subtleties arise when we perform an arithmeti operation in whi h the operands have dierent types. Suppose we assign an int expression to a float variable. or even simply if you store one type of number into a variable of another type. C++ will . and ould be said to perform su h a tions reasonably well. be ause it an be written exa tly as 6. However.

rst onvert the expression into the oating point format. So essentially some pre ision ould be lost. x=y.6. . There ould be loss of pre ision also if we assign a float expression to an int variable. Consider: int x=10. An int variable will have 31 bits of pre ision ex luding the sign. float y=6. whereas a float variable only has 24 bits or so.

After the expression is evaluated. If the two variables dier in size. then the result is also omputed to be of the same type. Thus if you write x=y+0. Do not distribute 51 The value 6. If your program asks to perform arithmeti operations on operands of dierent types.. The rules for this are fairly natural. Basi ally. i. int. there may have to be a further type onversion. when a oating value is to be stored into an integer. the integer losest to y. At the end. then the smaller is onverted to have a larger size. and hen e the value in xyz is .e. If they are.5. We always onvert less expressive variables to more expressive ones. where var1 is int and var2 oat. If var1. long then both will be onverted to double. This you an obtain for yourself by adding 0. Abhiram Ranade. You might want the assigned value to be the losest integer. var2 are long. and so on. When we perform arithmeti operations. If the operands are of type float.0 is by default onsidered to be of type double. then the operands must be onverted so that they have the same type. then var2 will be onverted to long. 2011. the fra tional part is dropped. or it might have to be stored into a variable.0 where xyz is of type float? The key point to note is that a oating literal like 100. In both ases. it is ne essary that the operands be of the same type. then x would be ome 7. where unsigned int are onsidered least expressive. x will equal 6. int more expressive than that and float most expressive. it may either itself form an operand in a bigger expression. C++ uses trun ation. The above dis ussion leaves open the question: what happens when we write xyz*100. so C++ tries to do the best it an: it keeps the integer part.6 is not integral. Then var1 will be onverted to float. Suppose we have an arithmeti expression var1 op var2.5 before the assignment.

of ourse. You an spe ify literals of spe i.rst onverted to double and then the produ t omputed. The produ t. has type double. An integer literal is likewise onsidered to be of type int.

0/x.e. As per the rules stated.U whi h respe tively stand for long. Thus if you write 100LU. Thus the exa t quotient 3. z = 360. float y. having the value 100.z.F.6 will be trun ated to give 3. i.0/x one of the operands is float. hen e the result will be evaluated as a oat. 3. 360/x will be evaluated to have an integer value sin e both operands are integer. unsigned. Here are some simple examples. w = 360. In the next statement. 360. w. types by atta hing the suÆxes L. oat. int x=100. it will be interpreted as a literal of type long unsigned. This value will be stored in z. In the . This value will be stored (after onversion to the oating point format) into y.6. y = 360/x.0/x.

2. the value of the expression will indeed be 3.6.3 Expli it type onversion It is possible to onvert an expression exp of numeri al type T1 to an expression of type T2 by writing either . however be ause w is of type int. there will have to be a type onversion. 3. and as a result the value stored in w will be just 3.nal statement.

say z = 1. Abhiram Ranade. the rightmost assignment operator is evaluated . i. given an expression x = y = z = 1. 2011. This will end up assigning 1 to all the variables. but the expression stands for the value that got assigned.g. The type onversion rules as des ribed earlier apply.4 Assignment expression It turns out that C++ allows you to write the following ode. int(6.z. Any assignment. Further. Not only is the assignment made. This has a systemati explanation as follows. e.4) would evaluate to the integer value 6.y. int x.2. the asso iativity of = is right-to-left.e. Do not distribute 52 T2(exp) or (T2) exp This latter form is a lega y from the C language. 3. x = y = z = 1. is also an expression in C++.

Thus. in whi h the evaluation order is left to right. su h as the arithmeti operators. Now the expression inside the innermost parentheses.rst. This is dierent from the other operators you have seen so far. z = 1 is required to be evaluated . is really to be read as x = (y = (z = 1)). the our statement x = y = z = 1.

Now the statement ee tively be omes x = (y = 1). and then x to 1.3 Examples We onsider some simple examples of using the data-types and assignment statements. main_program{ float entigrade. out << "Give temperature in Centigrade: ".0 + entigrade * 9. 3.0. in >> entigrade.0/5.rst. The exe ution ontinues by setting y to 1. Here is a program that reads in the temperature in Centigrade and prints out the equivalent temperature in Fahrenheit. .6. fahrenheit. This not only puts the value 1 into z. but itself evaluates to 1. out << "Temperature in Fahrenheit: " << fahrenheit << endl. These do not in lude the bool type whi h is onsidered in Se tion 5. } fahrenheit = 32.

in >> small. the ASCII value of the letter typed in by the user is pla ed in small.'a'. Further. But this dieren e is the same for all letters. Sin e small ontains 113. exe utes. 3. repeat(10){ forward(i*10). 'q' is pla ed in small. The upper ase letters A-Z also have onse utive ASCII odes. and it prints out the same letter in the upper ase. we an add to it 'A' . Note we ould have written 9 instead of 9. The operator * exe utes before / be ause it appears to the left. . This is be ause that while multiplying entigrade. apital = small + 'A' . From this it follows that for all letters. right(90).0 and 32. we need to note an important property of the ASCII odes.32. But what we have written is preferable be ause it makes it very lear that we are engaging in oating point arithmeti . sin e entigrade is float. Do not distribute 53 Note that the operator + is exe uted last be ause it has lower pre eden e than * and /. To omplete the example. whi h when printed out displays the a tual upper ase letter. out << "Type in any lower ase letter: ". apital. the dieren e between the ASCII ode of the upper ase version and the lower ase version is the same. Abhiram Ranade. The lower ase letters a-z have onse utive ASCII odes. When the statement in >> small. apital would get 113 . Suppose as an example that the user typed in the letter q.e. main_program{ har small. So this value gets pla ed in apital. i.'a'.0. Hen e given the ASCII ode value for any lower ase letter. note that the ASCII ode of 'A' is 65. 'A'-'a' merely gives the numeri al dieren e between the ASCII odes of upper ase and lower ase of the letter a. } out << apital << endl.4 Assignment with repeat What do you think happens on exe uting the following pie e of ode? main_program{ turtleSim(). 2011. int i = 1. be ause 'A' and 'a' denote the integers representing the ASCII odes of the respe tive letters. 81.0. This value happens to be 113. it would get onverted to a oat value anyway. Then its ASCII value. To understand the next statement. Thus 'A'-'a' is -32. In the next program you are expe ted to type in any lower ase letter. This is indeed the ASCII ode of Q as required. Similarly we ould have written 5 and 32 instead of 5. and this will give us the ASCII ode of the orresponding upper ase letter.

and draw the lines tra ed by the turtle as it moves. Imagine that you are the omputer and exe ute the ode one statement at a time. } } wait(5). You will probably be able to . Write down the values of dierent variables as you go along. Do not distribute 54 forward(i*10). right(90). i = i + 1. 2011. Abhiram Ranade.

It is strongly re ommended that you do this before reading the explanation given next. In the .gure out by exe uting 2-3 iterations.

we need to . We next see another ommon but important intera tion of the assignment statement and the repeat statement. For this.rst iteration of the repeat. i. the turtle will tra e a \spiral" made of straight lines. Consider the following problem. a larger distan e in ea h iteration. The turtle goes forward 10*i. from the keyboard. As you will see.e. i will have the value 1. We want to read some numbers. and print their average. and this value will in rease by 1 at the end of ea h iteration.

rst .

The . main_program{ int ount. is exe uted in ea h iteration. This an be done as follows. sum = sum + num.1 Programming Patterns There are two important programming patterns used in the programs of the previous se tion.4. and before it is exe uted.sum=0. repeat( ount){ out << "Give the next number: ". in >> ount. 3. Thus in the end sum will indeed ontain the sum of all the numbers given by the user.nd their sum. Thus in ea h iteration the number read is added into sum. out << sum/ ount. out << "How many numbers: ". out << endl. in >> num. The statement sum = sum + num. } } out << "Average is: ". the next number has been read into num. float num.

rst pattern is what we might all the sequen e generation pattern. Note the value of the variable i in the .

As you an see. and so on. by hanging the starting value for i and adding a dierent number to . and then be ame 2.rst program. It started o as 1. then 3.

55 Abhiram Ranade. we ould make i take the values of any arithmeti sequen e (Exer ise 5). Do not distribute inside the loop instead of 1. 2011. You will .

Will using max help us ompute the value of the maximum of the values read? In other words. where max(a. and that happened to be zero. vn. You might wonder whether this idea only works for addition or might work for other operators as well. suppose the number of numbers read is n.b. For example C++ has the ommand max. : : : . Then after the exe ution of the loop in the se ond program the variable sum has the value: 0 + v + v + + vn Here we have written 0+ expli itly to emphasize that the value al ulated a tually also depends on the value to whi h sum was initialized. but it is a hoi e we made. The variable sum was initialized to zero.nd this pattern helpful in solving many problems. and suppose the values read were v . what would happen if we de. The se ond pattern is what we might all the a umulator pattern. and then the number read in ea h iteration was added to the variable sum. The variable sum was thus used to a umulate the values read in ea h iteration.b) gives the maximum of the values of the expressions a. Stating this dierently. This was seen in the se ond program.

8 that it suÆ es to hoose -numeri al limits<float>::max(). so that the values vi annot be even smaller. There is another way to do this also. v ). v . We know from Se tion 3. If all numbers are negative. whi h is not the maximum. whi h you might . in the program. note that we a tually have a hoi e in de iding how to initialize maximum.ned a variable maximum and wrote i 1 1 2 maximum = max(maximum. assuming n = 4 and also assuming that maximum is initialized to 0 just as sum was.? For simpli ity. num) instead of sum = sum + num. Clearly.1. whi h we put in pla e of the statement sum=0. we should initialize it to as small number as possible. v ) Will this return the maximum of v . v ? As you an see this will happen only if at least one of the numbers is positive. v ). the value taken by maximum at the end of the repeat will be: max(max(max(max(0. Before we abandon this approa h as useless. Thus our initialization be omes: 1 1 2 3 2 3 4 4 maximum = .numeri al_limits<float>::max(). then this will return 0. v ). v .

We ould merely read the .nd simpler.

and assign maximum to that. out << "How many numbers: ". Thus the program just to al ulate the maximum of a sequen e of numbers will be as follows. main_program{ int ount.rst value of num. . be ause we read one number earlier. in >> ount. Note that we now repeat only ount-1 times.

Turns out that for a variable C. The operator ++ written after a variable is said to be the (unary) post-in rement operator. and so your ode will be read by others. } repeat( ount-1){ out << "Give the next number: ". We re ommend that you avoid a statement su h as y=x++. means C = C . } out << "Maximum is: " << maximum << endl. As an expression C-. and is alled the post de rement operator.. Abhiram Ranade. possibly onfusing.num). You may also write ++C. be ause it is less onfusing. y = ++x. C--. x++.y would get the value 3. 2011. we des ribe some additional. This tends to o ur quite frequently in C++ programs. out << "Give the next number: ". It is worth noting that in the modern era programming is often done by teams.. and instead write it as the less onfusing y=x. whi h merely means C = C + 1. after exe ution y would be 2 and x would be 3. feature of the ++ operator. 3.maximum. in >> num. Thus if you wrote int x=2.y=x. both x.y. This is also a very useful operator. it is re ommended that you use the expression forms sparingly. C++ is also an expression. It stands for the value that C had before 1 was added to it. For ompleteness. ++C also has a value as an expression: ex ept the value is the new value of C. whi h is the unary pre-in rement operator operating on C. . This usage is very useful. Again this will usually be better written as ++x. So it is good to write in a manner that is easy to understand qui kly. This also auses C to in rease by 1. in >> maximum. Thus if you wrote int x=2..y. you have the pre-de rement operator with all similar properties.2 In rement and de rement operators A key statement in the sequen e generation pattern is i=i+1.has the value that C had before the de rementation. So a short form has been provided. In general you may write C++. where C is any variable. Again. Likewise. Analogously.4.1. y = x++. Do not distribute 56 float num. maximum = max(maximum..

you an explain why you have written the program as you have. Likewise text starting with the hara ters /* and ending with */.4. /=.. By writing omments. Analogously C++ has operators *=. where vname is a variable name. Its purpose is to put in explanatory or auxiliary information (e. and expr an expression. It is re ommended that you use these expression forms sparingly. The expression forms of the operator += and others are also quite rypti and hen e onfusing. A omment annot be exe uted. when was the program written and by whom) along with the ode. Abhiram Ranade. so that other programmers (or you yourself rereading after some time during whi h you might forget) an understand your ode. 2011. The phrase vname += expr is also an expression and has as its value the value that got assigned.3 Compound assignment operators The a umulator pattern ommonly needs the statement vname = vname + expr. and -=. 3. Do not distribute 57 3.5 Comments Text beginning with two slashes // and going all the way to the end of line is said to onstitute a omment. This an be written in short as: vname += expr. Use the .g. These operators are olle tively alled the ompound assignment operators.

repeat( ount-1){ // we already read one number into maximum. maximum = max(maximum. in the last program of Se tion 3. This ould be explained by writing a omment. out << "How many numbers: ".1 it is not obvious why we wrote repeat( ount-1)f . int ount. For example. in >> num. Thus the program ould have been written as main_program{ // read in given number of numbers and print maximum. g rather than the more natural repeat( ount)f ... out << "Give the next number: ". Also.num). g.. so we // need to read only ount-1 more. it is a good idea to put a omment at the top of the program explaining what the program does.4. .. out << "Give the next number: ". } } out << "Maximum is: " << maximum << endl. in >> maximum.maximum. in >> ount. float num. and the se ond format if you want a long omment.rst format if you want to put in a short omment.

you will write larger and larger programs. // sum of marks read so far. that is indeed the best. then omments will explain to that person why you wrote what you wrote. float temperature. If the ode itself makes the motivation lear. The omments should not repeat what is obvious from reading the ode.6 Data invariants De. As you get better at programming. In that ase leave it alone! 3. float markSum. as will be the ase if you work in a team. Writing good omments is an art. In fa t. In that ase. // in degrees Kelvin Comments are very important. Do not distribute 58 Here are some additional examples of omments that might appear in your ode. the omments will help you remember. you may yourself forget why you wrote something after a while. If somebody else is to read them. Abhiram Ranade. 2011.

But that doesnt mean variables should be de. as you have seen.ning variables is easy.

When we de.ned asually.

Indeed. though this is also a bit trivial. Thus this is also true. At the beginning sum is 0 and nothing is read. we should have a good idea in mind about the role it plays in the program. be ause ount does not hange at all. Finally onsider (3). We an observe that after reading into ount subsequent reading happens only into num.e. and (3) the variable sum for keeping tra k of the sum of the values read till any point in the program. although it is somewhat trivial. and the user is expe ted to type in the number of values to be read at the beginning. And this idea should be arti ulated. and what is read is expe ted to be a value to be averaged. and hen e at this time the invariant is satis. Invariants are useful for arguing that our program is orre t. i. (2) the variable num will be used to read ea h value. we an say (1) the variable ount will be used to keep tra k of the number of values to be read. Indeed we an onsider 0 to be the sum of the values in an empty set. what values it takes and what those values represent. For example. we read into ount at the beginning of the program. or with several variables. Can we laim these as invariants? Consider (1). An invariant an be asso iated with a single variable. in the program for al ulating the average of a sequen e of numbers. Consider (2) next. Su h an arti ulation is alled an invariant asso iated with that variable.ne a variable. So (1) is an invariant.

To see that the invariant is satis.ed.

// statement 1 // statement 2 and there are no other statements that modify either num or sum. sum = sum + num.ed even subsequently.. Suppose now that the invariant is satis.. as . . let us observe that the statements in >> num. i.. and sum = sum + num. o ur only in su ession..e. in >> num.

sum is indeed the sum of values read till then (or 0 if nothing has been read). i.e.ed before exe uting statement 1 in the ode above. Now statement 1 will read in .

Abhiram Ranade. Thus after statement 2. 2011. Do not distribute 59 a value. our invariant will immediately be satis. and statement 2 will immediately ause that value to be added to sum.

Note that just after statement 1 our invariant is not satis.ed.

We also know by invariant (2) that all values are eventually read into num. For example. from invariant (3) it follows that sum ontains the sum of values read.ed: sum does not ontain the ee t of the value just read. The purpose of writing down invariants is to assure us that our program works orre tly. Su h momentary violations of the invariant are inevitable in general. at the end of exe ution the invariants must hold. But we should be lear about where the violations an happen. Also. So when we .

this an be a strategy for designing programs! We will also see examples of this. Invariants an be used in a dierent way. and hen e we must be getting the average.nally divide sum by ount we must indeed be dividing the sum of all values.7 Con luding remarks The . and then write a program that makes sure that our invariants hold no matter what happens. we an write down the invariants for our variables before we write a program. 3. Later on we will see invariants whi h are more interesting. whi h they indeed are. You might think that the invariants we have mentioned are too obvious. In fa t. If our invariants are arefully onstru ted.

rst step in omputing with numbers is to reserve spa e in memory for the number. Statements whi h do this are alled de.

A de.nitions.

We noted that the statement is somewhat subtle. As dis ussed in Chapter 2. How we interpret the bits depends upon the type of the variable. Of ourse. and the data stored in the variable is said to be the value of the variable. when it refers to the memory asso iated with the variable. i. Writing this down is useful for giving a proof that your program works orre tly. We also saw two important programming patterns: sequen e generation. and yet another for a variable of type float. and a umulation. As we dis ussed. what is stored in memory is always a sequen e of bits. ex ept when the name appears on the left side of an assignment statement. another for a variable of type int. whi h are in orre t in mathemati s but whi h have are meaningful in omputer programs.nition reserves the spa e and also gives it a name. These will ome up in the exer ises and in later hapters.e. You should go over your program to make sure that you are using it for the laimed purpose and the laimed purpose alone. we almost always refer to the value stored in the variable. together with its name. is said to onstitute a variable. . Perhaps this observation is useful to prevent being onfused by statements su h as p = p + 1. it is important that you have a very good idea of what you will use ea h variable for. When we refer to the name of a variable in a program. be ause of issues su h as rounding. and onverting between dierent types of numbers. the same pattern of 32 bits might mean one value for a variable of type unsigned in. whatever is the value on the right hand side is to be stored in this memory. The reserved spa e.

022E23 + 1 . Answer for three ases. when x is de. 60 Abhiram Ranade. ( ) x=6.022E23 * 6.0/7. What is the value of x after the following statements are exe uted? (a) x=22/7.6. 2011. Do not distribute 3. (b) x=22.8 Exer ises 1.022E23 .022E23 (d) x=6.6.022E23 + 1 (e) x=6.022E23.

float.ned to be of type int. double. exe ute and he k your on lusions. You may noti e that inf is printed in one ase { this is short for in. Put these statements in a program.

I have many hoi es in performing this omputation. and I an hoose the data type I use for representing the .b. 2. I an hoose the order in whi h to perform the multipli ations and divisions.nity and happens when the number in onsideration has be ome bigger than what C++ an represent in the given type. For what values of a. will the expressions a+(b+ ) and (a+b)+ will evaluate to dierent values? 3. I want to ompute the value of = .

nearly the orre t answer.0/6 * 99/5 * 98/4 * 97/3 * 96/2 * 95/1. int z = 100/6 * 99/5 * 98/4 * 97/3 * 96/2 * 95/1. int v = 100.0/1 * 99/2 * 98/3 * 97/4 * 96/5 * 95/6.3? Write down your answer without running the program. 4. i. out << u << " " << v << " " << w << endl. or the wrong answer. what are the values of the dierent variables and what is on the s reen. Here is a program whi h does it in several ways. int y = 100/1 * 99/2 * 98/3 * 97/4 * 96/5 * 95/6.0 * 99 * 98 * 97 * 96 * 95/ (1 * 2 * 3 * 4 * 5 * 6). int u = 100. 100 6 100 1 99 98 97 96 95 2 3 4 5 6 main(){ int x = 100 * 99 * 98 * 97 * 96 * 95/ (1 * 2 * 3 * 4 * 5 * 6). What is the state of the omputer.e. Then modify the program so that it prints the values after ea h iteration and also waits a few se onds so you an see what it has drawn at that point. int w = 100. after 4 iterations of the loop of the spiral drawing program of Se tion 3. Run the modi.nal and intermediate results. } out << x << " " << y << " " << z << endl. Then run the program and he k whi h of your guesses are orre t. Guess whi h of these are likely to give the orre t answer.

ar. arn. d. : : : . Write a program that prints the arithmeti sequen e a. Write a program that prints out the geometri sequen e a. a + nd. taking a. 5. r. ar . 2 . a + d.ed program and he k whether what you wrote down earlier is orre t. n as input. n as input. : : : . 6. a + 2d. Take a.

all with the same enter. The sidelength should in rease by q starting at side. It should draw nsquares as many squares. Abhiram Ranade. Write a program whi h reads in side. q. nsquares. 2011. Do not distribute 61 7. Repeat with the modi.

int i=0. 8. right(90). the user types in two digits. i++. 9. What does the following program draw: main(){ turtlesim(). } repeat(30){ left(90). Write a program whi h prints out the squares of numbers from 11 to 99. You are to . The ASCII odes for the digits will then be pla ed in p. forward(200*sine(i*10)). forward(10). The ASCII odes for the digits 0 through 9 are 48 through 57. ation that the sidelength should in rease by a fa tor q. } 10. Suppose in the third statement below.q. forward(-200*sine(i*10)).

. in >> q.dig2.ll in the blanks in the ode su h that dig1 gets the value of the digit in p (not the value of its ASCII ode). har p. dig1 = .q. then p.12.. in >> p >> q. n = . dig2 = . if the user typed '1'. For example. . int dig1.n.2. // equivalent to in >> p.n to be respe tively 1.q will ontain the values 49. At the end we would like dig1. Write a program that takes as input the oordinates of two points in the plane and prints out the distan e between them..'2'.50... Finally. the integer n should ontain the value of the number in whi h p is in the tens pla e and q in the units pla e. 11.. and similarly dig2 should get the value of the digit in q.dig2.

name is a quoted string meant to be the name given for the anvas.1 initCanvas To a ess the more general graphi s fa ilities. Yes.". anvas height() return the width and height of the anvas in pixels. The basi idea is: any ommand you used in Chapter 1 to ae t the turtle will also work with these turtles. the two joined together by a dot: \. that move on the s reen. respe tively named t1. if we ould have other shapes. You may also invoke the ommand as initCanvas(name. and y oordinates downward. t3 at the enter of the window reated either using turtleSim() or CreateCanvas(). wouldnt it be ni e to have several turtles that move or even draw lines simultaneously? It would also be ni e. This opens a window.2 Multiple Turtles We an reate multiple turtles very easily. Thus. For example. we merely write: 62 . it would be ni e to have moving ir les rather than triangles. 4.Chapter 4 Simple pp graphi s The graphi s ommands we introdu ed in Chapter 1 are quite limited. t2. by writing: Turtle t1. you must write the ommand following the name of the turtle. the turtles will all be at the enter. rather than just triangles.h). This will reate 3 turtles.t3. Many of these things are supported in simple pp.t2. The oordinate system of the anvas is unusual: the origin is at the top left orner. it is more onvenient to use the ommand: initCanvas(). Commands anvas width(). sta ked one on top of the other. For one thing.h should indi ate the width and height you desire for the anvas window. and x oordinates in rease leftward. as we will see in this hapter. 4. and w. but does not reate a turtle at its enter. For this. We next see how we get them untangled. to move turtle t1 forward by 100 steps. but you must say whi h turtle you are ae ting.w. if we want to reate an animation of boun ing balls.

Turtle t1. aligned at 120 degrees to ea h other. y. t2.forward(100). to turn t2 we would write t2. Cir les an be reated by writing: Cir le 1( x. Here is a program whi h will use 3 turtles to draw 3 o tagons. Do not distribute 63 t1. and the x and y oordinates of its enter.left(360. 2011. t2. t2. Abhiram Ranade. Here. t2.left(360.0/8). t3.forward(100).0/8). The same thing applies to other ommands su h as right. repeat(8){ t1. penUp.left(360. An axis parallel re tangle is de.3 Other shapes besides turtles Three other shapes are allowed besides turtles: ir les and axis-parallel re tangles. and straight line segments. t3. main_program{ initCanvas(). x. t3. penDown. The reated ir le is named 1. Likewise.r must be numeri al expressions whi h indi ate the radius of the ir le. y.r).forward(100).left(120).left(90).left(240).0/8). 4. } } wait(5).forward(100). t1. t3.

where x.Ly).ned as follows Re tangle r1( x. A line segment an be de. y.Ly the width and height respe tively. y should give the oordinates of the enter.Lx. and Lx. The reated re tangle has name r1.

y1.y2).x2. .ned as: Line line1(x1.

y1 are the oordinates of one endpoint.moveTo(x. The ommand Text t1(x.200. where the former moves the shape to oordinates (x. Abhiram Ranade.dy). s. In addition.y). 2011. You an hange the size of a shape also. it is also onsidered a kind of shape.setS ale(fa tor).200). Here relfa tor.4 Commands allowed on shapes Ea h shape mentioned above an be made to move forward and rotate. If we want to write text on the s reen.message). in whi h x.y2 the oordinates of the other. based on whi h its size is displayed.s ale(relfa tor).y are numbers and message is a text string an be used to write the message on the s reen. and x2."C++"). whi h is initially set to 1.move(dx. and the latter displa es the shapes by (dx. Do not distribute 64 This reates a line named line1 where x1. The .dy) from its urrent position. s. Every obje t maintains a s ale fa tor.y. So you might use the ommand Text txt(100. fa tor are expe ted to be double. and it has a pen at its enter whi h an be either up or down. s.y) on the s reen. 4. for any shape s. to write the text C++ on the s reen entered at the position (100. we have the ommands s.

rst version multiplies the urrent s ale fa tor by the spe i.

at the urrent position of s. The new image overwrites older images. You an rotate shapes ex ept Re tangle and Text using the left and right ommands as for the shape Turtle. whi h an be rotated. Then the following ommand auses an image of the shape to be printed on the anvas. You an print as many images of a single shape as you desire.ed relfa tor. the se ond version sets the s ale fa tor to fa tor. s. the shape might move away. Suppose s is a shape.imprint(). but the image stays permanently. You an also de ide whether a shape s is to appear in outline. if any. After this. Later on we will see the Polygon shape. or it is to be .

where v must evaluate to true or false.setFill(v). This ommand does not apply to Line shapes. use the ommand s. For the former.lled with some olor. The olor an be spe i.

.setFillColor( olor).ed by writing: s.

Do not distribute where olor is spe i. 65 Abhiram Ranade. 2011.

Suppose the user li ks at a point (x.y) on the s reen.100. It auses the program to wait until the user li ks. main_program{ int li kPos. you ould have Cir le (100.1 Resetting a shape For ea h shape ex ept Turtle. s.hide(). respe tively. and re reates the shape using the new values.ed for example.show().5 Cli king on the anvas The ommand getCli k() an be used to wait for the user to li k on the anvas.6 Proje tile Motion We will now write a program that simulates the motion of a proje tile. and then prints out the oordinates of the point at whi h the user li ked. as COLOR("red"). You may hide or unhide a shape s using the ommands s. .15). the following program waits for the user to li k. Note the spelling. For simpli ity assume that the 2 .100. wait(1). so this is upward velo ity). li kPos = getCli k(). other standard olor names an be used.4. initCanvas(). This would have the ee t of expanding the ir le. Suppose gravitational a eleration is 0. Suppose that the proje tile has initial velo ity 1 pixel per step in the x dire tion. and -5 pixels per step in the y dire tion (note that the y oordinate grows downward. } out << "Cli k position: ("<< li kPos/65536 <<".20). As an example. Instead of red. " << li kPos % 65536 <<")\n".init(100. For example. This ommand takes the same arguments as required for reation. 4. an init ommand is provided.1 pixels per step . 4. Then the value 65536*x+y is returned by the ommand. 4.

Cir le sp(5. 2011. a Cir le at the li k position. The proje tile is moved for 100 steps. Then it moves the proje tile as per its velo ity. main_program{ initCanvas("Proje tile motion".vy). double vx=1.1 gets added to the y omponent velo ity.penDown(). The pen of the proje tile is put down so that the path tra ed by it is also seen.1). 500. 66 Abhiram Ranade. vy += .1.vy=-5. sp.move(vx. } repeat(100){ sp. } The program waits for the user to li k.500). It then pla es a proje tile. start % 65536)).0).Position(start /65536. Do not distribute velo ity only hanges at the end of ea h step: at the end of ea h step 0.7 Best . wait(0. 4.Position(0. int start = getCli k().

(x .t straight line Suppose you are given a set of points (x . y ). (xn. Your goal is to . yn). : : : . y ).

We will see a way to do this assuming a spe i.nd a line y = mx + whi h is the losest to these points.

de.

nition of \ losest". A natural de.

d 0 = dm n X i=0 (yi mxi )2 = 2 n X i=0 xi (yi mxi The terms of this an be rearranged as an equation in m and : X X X m xi + xi = xi yi 2 i i i ) .e. the derivative of the sum must be 0. Instead. sin e the quantity yi mxi an be positive or negative. i. we will onsider the \verti al" distan e yi mxi . At the hosen value of m. i. su h that the above quantity is minimized. we will instead minimize the sum of the squares of these quantities.nition of the distan e from a point to a line is the perpendi ular distan e. 1 1 2 n X min (yi 2 mxi i=0 )2 Basi ally we have to sele t m. a tually. We will try to minimize the total distan e of all points from our line.e. the above sum must be smallest.

m X i P P xi + n = P X mxi ) yi i P De. 67 Abhiram Ranade. Do not distribute We an get another equation by asserting that the quantity to be minimized be ome as small as possible for the hosen value of . or at that value the derivative must be ome 0: 0= n dX (y d i=0 i ) mxi 2 n X = 2 (yi i=0 This an also be rewritten as an equation. 2011.

So we imprint the point. These equations are easily solved symboli ally. the pla ed point will vanish in the next iteration.8 Con luding Remarks If it appears to you that de. r = i xi yi. Note that we annot just pla e a point at the li ked position. 4. giving 2 m= nr qs np q 2 = ps qr np q 2 The exer ises ask you to write the program. Then our equations are pm+q = r and qm + n = s. and s = i yi. q = i xi .ne p = i xi .

ning shapes is like de.

ning variables.10). statement su h as: Cir le 1(100.15).100. 2(300. does indeed de.200. you would be right! Indeed.

25 for the y axis. Re tangle. 1 and 2. C++ allows reation of data types su h as these. These are spe ial data types reated for simple pp. multiples of =2 for the x axis.g. Use the repeat statement properly so that your program is ompa t. . the names of the shapes. For now.ne two variables. Line. Hint: Use the imprint ommand. Plot the graph of y = sin(x) for x ranging in the interval 0 to 4. Further. 4. Turtle in fa t are the data types of the orresponding variables.9 Exer ises 1. 2 are in fa t variables. you an just use them. Draw the axes and mark the axes at appropriate points. But from the view of the C++ ompiler. We will study this in Chapter 14. The ommands dis ussed above are invoked on these variables. e. 1. Cir le. and as a result they ause the images on the s reen to be hanged. Draw an 8 8 hessboard having red and blue squares. and multiples of 0. 2.

For example. the velo ity should be taken to be proportional to the distan e between the proje tile (. 2011. 68 Abhiram Ranade. Do not distribute 3. Modify the proje tile motion program so that the velo ity is given by a se ond li k.

At what angle does the proje tile go farthest? 5. Write the program to . Modify the proje tile motion program to tra e the traje tories of the proje tile for the same initial velo ity and dierent angles. The horizontal distan e overed by the time the maximum height is rea hed is u gu . then maximum height rea hed is ug . 4. and g the gravitational a eleration. y dire tions. For this you may note that if ux.rst li k) and the se ond li k. Or you an require the se ond li k to be the highest point rea hed by the proje tile as it moves. uy are the initial velo ities of the proje tile in the x.

nd the best .

y) pair.0). You should a ept the points by letting the user li k on the anvas. Derive the best . You are further told that the proje tile is surely known to pass through the origin (0.t line. Suppose you are given some observed positions of a proje tile. 6. Ea h position is an (x.

0).t traje tory for the given points. Write a program that waits for the user to li k thri e on the anvas and then draws a ir le through those 3 points. 7. 2 y 2 x y . su h that it passes through (0.

The a tual rules of in ome tax al ulation are quite omplex. Let us onsider very simpli.Chapter 5 Conditional Exe ution Suppose we want to al ulate the in ome tax for an individual.

000.ed rules as follows: For males.000 and Rs.000 then you pay 10% of the amount by whi h your in ome ex eeds Rs. otherwise exe ute some other statement. 92. 1. 500. then you pay Rs. This onditional exe ution is required for the tax al ulation above. or ea h statement was exe uted a ertain number of times.000. then exe ute a ertain statement. If your in ome is between Rs. and how it an be stored in the bool type.000 plus 20% of the amount by whi h your in ome ex eeds Rs.000. 32. The statements that we have learned do not allow us to express something like \If some ondition holds. 180. ea h statement was exe uted on e.000. If your in ome is between Rs. 800.000. If your in ome ex eeds Rs. We also dis uss logi al data. We will also dis uss the swit h statement. 500. then you pay Rs. The main statement whi h expresses onditional exe ution is the if statement. there is no tax if your in ome is at most Rs.80. 500. whi h is sometimes more onvenient.1 The If statement We .000.". 5. 800.000 and Rs. In the programs that we have written so far.000 plus 30% of the amount by whi h your in ome ex eeds Rs. as a part of a repeat blo k. 800. 180.

and then explain ea h statement. if(in ome <= 180000) tax = 0. main_program{ float in ome. out << "What is your in ome in rupees? ". // in rupees. if((in ome > 180000) && (in ome <= 500000)) tax = (in ome . float tax.180000)* 0.1.rst give the program whi h al ulates the tax. in >> in ome. 69 // first if statement // se ond if statement . // in rupees.

e. This program uses the simple form of the if statement.>.==.3. and not equal. if ( ondition) onsequent In this the onsequent an be any statement. greater than. greater than or equal.g. <.500000)* 0. The simplest form is exp1 relop exp2 where exp1 and exp2 are numeri al expressions. } // third if statement // fourth if statement out << "Tax is: " << tax << endl. 70 Abhiram Ranade. less than or equal.<=.2. whi h is as follows. Do not distribute if((in ome > 500000) && (in ome <= 800000)) tax = 32000+(in ome . Thus in the .>=. If the ondition is false. 2011. whi h is exe uted if the ondition is true.800000)* 0. equal. then the onsequent is not exe uted. if(in ome > 800000) tax = 92000+(in ome . and relop is a relational operator. You have several examples of onditions in the ode above.!= whi h respe tively stand for less than.

Thus our ondition an be a onjun tion (and) of two or more onditions.. This is written as follows. then the ondition is true. . In other words.. Only in this ase is the tax set to (in ome . || onditionn 1 The single hara ter & is also an operator.e. the value of the variable in ome is at most 180000. the ompound ondition is true only if both the sub onditions. ondition1 && ondition2 && .1. i. in ome > 180000 and in ome <= 500000 are true. but it means something dierent. && onditionn The hara ters && should be read as \and". or is said to su eed. see Appendix G. Similarly. the ondition is false.. tax = 92000 + (in ome . In our se ond if statement. the ondition is in ome > 800000. we have an example of this.e. Note that we an have a ompound ondition whi h holds if at least one of some set of onditions holds.. in the last if statement. In other words. the ompound ondition is true only if the in ome is between 180000 (ex lusive) and 500000 (in lusive). in ome <= 180000 is a ondition. 10% of the amount by whi h the in ome ex eeds 180000. you want ondition1 to be true and ondition2 to be true. For example.180000)* 0. Here. It is possible to spe ify a more omplex ondition in the if statement. If during exe ution. and in this ase the onsequent is not exe uted. and is said to fail. you may wish to perform a ertain operation only if some two onditions are both true. If in ome is greater than 180000. Su h a ondition is said to be a disjun tion of (sub) onditions and is expressed as: 1 ondition1 || ondition2 || . i. and if so the onsequent is exe uted.800000) * 0. The onsequent here. Thus tax is set to 0.3 is exe uted if and only if the value of in ome is greater than 800000. tax remains un hanged.rst if statement in the program.

After printing out a message and reading the value of in ome.e. if the in ome is em not in the range 180000 (ex lusive) and 500000 (in lusive). one ondition an be the negation of another ondition. written as follows: ! ondition where the ondition ! ondition is said to be the negation of ondition.1. Finally. But the ! at the beginning negates this ondition. But this is the same ondition as tested in the se ond if statement in the program! It is important to learly understand how the above program is exe uted. We note that the se ond if statement an also be written as: if(!((in ome <= 180000) || (in ome > 500000))) tax = (in ome . The ondition ! ondition is true if ondition is itself false. the program exe utes the . the ompound ondition is true if ondition1 is true or ondition2 is true and so on. The exe ution is as usual. top to bottom. so the entire ondition is true only if the in ome is indeed in the range 180000 (in lusive and 500000 (ex lusive). 2011. i. Do not distribute 71 The hara ters ||. Abhiram Ranade. onstitute the logi al or operator. i. Noti e that (in ome <= 180000) || (in ome > 500000) is true if in ome is either less than or equal to 180000 or greater than 500000.e.180000)* 0. and ! ondition is false if ondition is true.

For this the ondition in it is he ked. In general. } . By putting statements into a blo k. if (in ome > 800000){ tax = 92000+(in ome . allows you to prevent su h unne essary he ks. the onditions have been so designed so that the ondition in only one if statements will evaluate to true.2 Blo ks In the if statement dis ussed above. the onsequent was expe ted to be a single statement.rst if statement. not just one. Note that on e we dis over a ertain ondition to be true. A blo k is simply a olle tion of statements that are grouped together in bra es. Suppose for example. The blo k onstru t helps us in this ase.g.g. e. as the onsequent part of the if statement. we need the notion of blo ks. So every if statement will be exe uted. we are making a single ompound statement out of them. and hen e only one onsequent statement will be exe uted. we would repla e the fourth if statement in the program with the following. as well as al ulate the tax.3. we want to print a message \This person is ri h!" if the in ome is more than 8 lakhs. we know that the other onditions annot be true.800000)* 0. dis ussed in the next se tion. But before dis ussing that. After this the se ond if statement is exe uted. f and g. we might want to exe ute several statements if a ertain ondition held. 5. A blo k an be pla ed wherever a single C++ statement is required. that the in ome is at most 180000. and then the onsequent is exe uted if the ondition is true. e. out << "This person is ri h!" << endl. So the natural question arises: why should we even he k them? The more general if statement.

Let us now note that the general form of the repeat statement is: repeat ( ount) a tion where a tion is any statement in luding a blo k. if ( ondition) onsequent else alternate In this the ondition is .3 Other forms of the if statement The if-else statement has the following form. Thus we may write repeat (10) out << "Test. Abhiram Ranade. Do not distribute 72 A tually." to be printed 10 times. 2011. 5. a blo k is really not new to you: you have already used it as a part of the repeat statement. whi h will ause the message "Test." << endl.

else if ( onditionn) onsequentn else alternate This statement is exe uted as follows. If no ondition is found true. until some onditioni is found to be true. ondition2...rst evaluated. then ondition2 is he ked. are exe uted in order. depending upon whether the ondition is true or false.. .e. float tax. If so. then the onsequent statement is exe uted. then the alternate is exe uted. ondition1 is he ked. . If the last line is omitted. If it is true. If ondition1 is false. then onsequent2 is exe uted. If it is false. If it is true. First. and that ompletes the exe ution of the statement. ondition1. then nothing is exe uted if none of the onditions are found true. i. It is a eptable to omit the last line. and that ompletes the exe ution of the statement. else alternate. So exa tly one out of the statements onsequent and alternate is exe uted.. Now we an rewrite our tax al ulation program as follows. if ( ondition1) onsequent1 else if ( ondition2) onsequent2 else if ( ondition3) onsequent3 . main_program{ float in ome. then onsequenti is exe uted. in >> in ome. and the exe ution of the statement ends. In general. The most omplex form of the if statement is as follows. If it is true. then onsequent1 is exe uted. out << "What is your in ome? ". then the alternate statement is exe uted.

rather than 4 as in the previous program.3.3. Thus even without he king this ondition we an dire tly set the tax to 92000+(in ome .800000)* 0. // new first if else if(in ome <= 500000) // new se ond if tax = (in ome . This is be ause if all the 3 onditions are false. else if(in ome <= 800000) // new third if tax = 32000+(in ome .800000)* 0. Noti e that this program ontains only 3 onditions. } out << "Tax is: " << tax << endl. Abhiram Ranade. we know that the in ome must be bigger than 800000.1. else tax = 92000+(in ome . 2011. Also note that the se ond and third onditions are mu h simpler! In the . Do not distribute 73 if(in ome <= 180000) tax = 0.500000)* 0.2.180000)* 0.

we know that the \new se ond if" is exe uted only if the ondition of \new . we he ked if the in ome was larger than 180000 and at most 500000.rst program. In the new program.

e. i. if the in ome was greater than 180000. But then.rst if" failed. The third if statement also simpli. we dont need to he k this again in the \new se ond if". So it suÆ es to just he k if in ome is at most 50000.

Further note that the original program would he k ea h of its 4 onditions no matter whi h one is true. whereas in this program as soon as the .es similarly.

the orresponding onsequent a tion is performed. and the subsequent onditions are not he ked.4 A dierent turtle ontroller The turtle driving programs we saw in hapter 1 required us to put information about the .rst true ondition is found. 5. Thus the new program is more eÆ ient than the previous program.

Our program must re eive these hara ters that the user types. Here it is. main_program{ har ommand. Let us de ide that the user must type the hara ter 'f' to make the turtle go forward by 100 pixels. The program would then move the turtle based on the user's response. i. and then move the turtle a ordingly. turtleSim(). and the hara ter 'l' to make the turtle turn left by 90 degrees. .e. the hara ter 'r' to make the turtle turn right by 90 degrees. the exa t sequen e of forward and turn ommands that we want to exe ute had to be written out in the program. The same program an then be used for drawing dierent pi tures. We will now write a program whi h during exe ution will ask the user to state how to move the turtle..gure we wanted to draw right into program. the user merely has to give dierent responses during the exe ution.

} } if(bLx-bWidth/2<= x && x<= bLx+bWidth/2 && bLy-bHeight/2 <= y && y <= bLy+bHeight/2) t.left(10). Abhiram Ranade.1 \Buttons" on the anvas We an build \buttons" on the anvas using the Re tangle shapes of Se tion 4. bWidth=150.bHeight=50. 'r') right(90). tL(bLx. We an ontrol the turtle by li king on the buttons.bLy=100. if(bFx-bWidth/2<= x && x<= bFx+bWidth/2 && bFy-bHeight/2 <= y && y <= bFy+bHeight/2) t. buttonL(bLx. 2011. The program begins by drawing the re tangles on the s reen."Forward"). Remember that har data is really numeri al.forward(100). Do not distribute } repeat(100){ in >> ommand. Text tF(bFx.bWidth.bFy. if ( ommand == 'f') else if ( ommand == else if ( ommand == else out << "Not a } 74 forward(100).bLy.bHeight). but . onst float bFx=150.bHeight). proper ommand. Turtle t.bLy.3. bLx=400. " << ommand << endl.bFy=100. main_program{ initCanvas(). Noti e that we have not given the oordinate information of the buttons by writing numbers dire tly. so it is perfe tly a eptable to ompare it using the operator ==. int y = li kPos % 65536. 'l') left(90). repeat(100){ int li kPos = getCli k()."Left Turn"). Try it! 5. int x = li kPos/65536.4. This gives yet another turtle ontroller.bWidth.bFy. Re tangle buttonF(bFx. This program will exe ute 100 user ommands to move the turtle before stopping.

rst reated the names bFx.bFy and so on having spe i.

you would have needed to . Using su h names is onvenient: if you want to adjust the layout of buttons later. you just need to hange the value of some name. values and then used these names in the button reation. Without names.

Abhiram Ranade. In the present ase. and the right edge oordinate must be larger or equal. And orrespondingly we must he k for the y oordinate as well. if you want to hange the width of the re tangles. instead of worrying in whi h all pla es the width value needs to be hanged. you just need to assign a dierent value to bWidth. i. the left edge oordinate must be smaller or equal. text is put in the re tangles. we see later how to make the loop inde. we wait for the user to li k. Next. Do not distribute 75 make hanges in every pla e the number appeared. We he k whether the li k is inside either of the two re tangles. This program will only allow 100 li ks. This is done in the two if statements in the loop. Then we go into a loop. 2011.e. Ea h he k has two parts: we must he k if the x oordinate of the li k is between the left edge of the re tangle and the right edge. Inside.

we do not exe ute the statements following the break but dire tly go to the statement in the program following the swit h statement.'' ase onstant2: group(2) of statements usually ending with ``break. i. First the expression is evaluated. then the exe ution needs to ontinue or \fall-through" to the next group.. in luding default-group statements. A similar situation arises in many programs. main(){ har ommand. statement. The general form of the swit h statement is: swit h (expression){ ase onstant1: group(1) of statements usually ending with ``break. depending upon whi h we took dierent a tions.nitely or stop if some ondition is met. If the value of expression is dierent from any of the onstant values mentioned..5 The swit h statement In the turtle ontrol program. We exe ute group(i) statements. 5. So C++ provides the swit h statement so that we an express our ode su in tly. Using a swit h our turtle ontrol program an be written as follows. there was a single variable. If the value is identi al to onstanti for some i. If a ertain group(i) does not end in a break. then group(i+1) statements and so on. turtleSim(). then the default-group of statements is exe uted. If we en ounter a break then the exe ution of the swit h is omplete. then we start exe uting group(i) statements. unless we en ounter a break.'' .e. ommand. repeat(100){ . Fall-throughs are onsidered to be rare. default: default-group of statements } The statement exe utes in the following manner.

It will fall through the ases 5. break.\n''. } } Suppose the input is 5. and then a break is en ountered. swit h( ommand){ ase 'f': forward(100).10 to ase 12. in >> month. Do not distribute } } 76 in >> ommand. Here is an example whi h has fall-throughs. Then the exe ution will start after the point labelled ase 5:. . ase 2: // February out << ``This month has 28 or 29 days. main(){ int month. taking n as the input. Suppose we want to print the number of days in the nth month of the year. break. break. } As you an see the new program is ni er to read. ase 'l': left(90). This will omplete the exe ution of the sele t. Abhiram Ranade.7. default: out << ``Invalid input. 2011.\n''. In this the number of days will be printed to be 31.\n''. ase 4: // April ase 6: // June ase 9: // September ase 11: // November out << ``This month has 30 days. Here is the program. break. ase 'r': right(90). break. " << ommand << endl. break.\n''. default: out << "Not a proper ommand. sele t(month){ ase 1: // January ase 3: // Mar h ase 5: // May ase 7: // July ase 8: // August ase 10: // O tober ase 12: // De ember out << ``This month has 31 days.8.

The resulting ombination will also be true or false.6 Logi al Data An important part of the if statement are the onditions. We have also seen that there may be several equivalent ways of writing the same ondition (as we saw for the se ond if statement of our . i. we an asso iate the value true or the value false with ea h ondition. 2011. We have already seen that a ondition is either true or false. Do not distribute 77 The swit h statement is onsidered somewhat error-prone be ause you may forget to write break. So be areful. We have also seen that onditions an be ombined in dierent ways.e. Abhiram Ranade. 5..

and an algebra for manipulating onditions. as just another kind of data? This turns out to be a very good idea. the right hand sides of the above assignment statements are onditions. After the exe ution of the above statements. You have already seen this data type in Chapter 3. highIn ome. 200000.rst program). As you an see. onditions are similar to numeri al expressions. and whatever the values these onditions have will been put in the orresponding left hand side variables. we an have numeri al expressions that are equivalent. why not treat onditions. Then we may write: bool lowIn ome. now we will do more interesting things with it. let us de. First we observe that we an assign values of logi al expressions to bool variables. or what we will hereafter refer to as logi al expressions was developed by George Boole in 1940. In this sense. midIn ome. midIn ome = (in ome > 180000) && (in ome <= 800000). true. lowIn ome = (in ome <= 180000). Suppose that in ome is a float variable whi h has already been assigned value. numeri al expressions an be ombined to build bigger numeri al expressions. highIn ome = (in ome > 800000). As another example. say Rs. false. midIn ome. In that ase. numeri al expressions have a value. and in honour of Boole the data-type for storing logi al data is named bool. highIn ome would respe tively have the values false. the variables lowIn ome. C++ supports the manipulation and storage of logi al data.

bool lowerCase.ne a bool variable that will be true if a hara ter read from in happens to be a lower ase hara ter. Note that this will happen if the ASCII value of the hara ter is at least 'a' and at most 'z'. lowerCase = (in_ h >= 'a') && (in_ h <= 'z'). To understand that program we will need to reason about expressions ontaining logi al data. Thus the ode for this ould be har in_ h. We will next onsider a more omplex program whi h determines whether a given number num is prime or omposite. in >> in_ h. So we . The ability to store logi al values will be useful in this program.

.rst dis uss this.

Thus. In a similar manner. Do not distribute 78 5. First. Abhiram Ranade. Similarly !x || !y is the same as !(x && y). the same ondition an be expressed in many ways. x && !x an be repla ed with false. More formally.6. Consider . false is said to be the identity for ||.1 Reasoning about logi al data As we dis ussed earlier. Or in other words. let us make a few simple observations. Thus false plays the same role with respe t to || that 0 plays with respe t to numeri al addition. we have that v || false has the same value as v. It is important to understand whi h expressions are equivalent. For any logi al value v. true is the identity for &&. This says that !x && !y is the same as !(x || y). Another rule is the so alled distributivity of && over ||. then false || false is learly false. it turns out that || also distributes over &&. Similarly. Likewise true && v has the value v for any v.z are boolean variables (or equivalently. The easiest way to he k this is to try out all possibilities: if v is true. Another important rule is that x || !x is always true.y. Finally. then true || false is learly true. then (x && y) || z is the same as (x && z) || (y && z). 2011. If v is false. onditions). an important rule is DeMorgan's Law. and hen e we an repla e su h expressions with true. if x.

In ome being at most 180000 is the same as it not being bigger than 180000.rst a ondition su h as in ome <= 180000. Hen e we an write this ondition also as !(in ome > 180000). While it is .

2 Determining whether a number is prime Determining whether a number is prime is an important problem. you should also be able to dedu e this given the rules given in this se tion.6. Here is the most obvious idea. We go by the de. We will only onsider the simplest (and hen e substantially slower than the fastest known) algorithms in this book. very fast algorithms are known. for whi h very sophisti ated.ne to be able to intuitively understand that the onditions (in ome > 180000) && (in ome <= 500000) and !((in ome <= 180000) || (in ome > 500000)) are the same. 5.

If we .nition. A number n is prime if it has no divisors other than itself and 1. So it should suÆ e to he k whether any number i between 1 and itself (both ex lusive) divides it.

nd su h an i then we de lare x to be omposite. So here is the ode fragment we should use: i=2.3. repeat(x-2){ /* . There we made i take 10 values starting at 1. This is really the sequen e generation pattern (Se tion 3.4. This requires us to generate all numbers between 2 and x 1 (both in lusive this time) so that we an he k whether they divide x.1) whi h we saw in the spiral drawing program of Se tion 3. otherwise it is prime. Now we want i to take the x 2 values from 2 to x 1.

3. and we update it in ea h step. i = i+1. 2011. } At the end of this found will indeed be true if any of the expressions (x % i) == 0 was true. repeat(x-2){ found = found || (x % i) == 0. In ea h iteration of the loop we an he k whether i divides x. So our ode fragment be omes: i=2. int i=2. for any value of i. And at the beginning we need to read in x et . Abhiram Ranade. the identity for the OR operation. Thus following this ode we simply print prime/ omposite depending upon whether found is false/true. We want to know whether any su h ondition su eeds. of the onditions that arise in ea h iteration. Then in ea h step of the loop we merely update found. i = i+1. exa tly as we updated sum in the average omputation program." << endl. Then we initialize it to false. The omplete program is as follows." << endl. We must maintain an a umulator variable whi h we set to the identity for the operator in question. else out << x << " is prime. But this is nothing but a logi al or. This program will be improved in several ways later. In other words. int x. main(){ //De ide if x is prime. But we know how to implement that! We saw how to do it to al ulate the sum in the average omputing program of Se tion 3.1. Say we name our a umulator variable found (sin e it will indi ate whether a fa tor is found). Do not distribute } 79 Here i takes values from 2 to x-1. */ i = i + 1. This is really the ondition (x % i) == 0. repeat(x-2){ found = found || (x % i) == 0.4. in >> x. this itself is the a umulator pattern mentioned in Se tion 3. found = false. } } if (found) out << x << " is omposite. On e we . bool found = false.

e. So why even do the remaining iterations? This is indeed orre t: if we are testing if 102 is prime. it annot be ome false. we will dis over in the . and no matter what we do later. if in some iteration x % i == 0 be omes true.nd a fa tor of x. i. we will set found to true.

i. In the next hapter we will see how this an be done.rst iteration itself that 102 is divisible by 2. 2 is a fa tor and that 102 is omposite. .e. So we should prematurely stop the loop and not do the remaining iterations.

The . and also by what angle to turn. Suppose y is given as 2011 and d as 62. Do not distribute 5. Modify the turtle program so that the user an spe ify how many pixels the turtle should move. Write a program that reads 3 numbers and prints them in non-de reasing order. 4. Write a program that takes as input a number y denoting the year and a number d. You may put spa es or newlines in the sequen e for readability.7 Exer ises 80 1. Suppose we wish to write a program that plays ards. Thus if the user types \f100 r90 f100 r90 f100 r90 f100" it should draw a square. and prints the date whi h is the dth day of the year y. 3. and says whether the year is a leap year or not a leap year. Write a program whi h takes as input a number denoting the year. Abhiram Ranade. 5. 2011. 2. then your program should print \3/3/2011".

6. 52. Write a program that takes a hara ter as input and prints 1 if it is a vowel and 0 otherwise.6. where n is to be read from the keyboard. you need to de ide how to store the numbers.9. 9. Thus the lub a e has the smallest denomination. and 1 respe tively. king. king and a e. queen. It should also print its fa tors.J.8. whereas the ja k. where the last 4 respe tively are short for ja k.7. 10. One possibility to store the least signi. 2. it should print \queen of spades". 1. First.10.2. or given 51. So given 20.0 to the suites respe tively. 13. The number assigned to a ard of suite s and denomination d is then 13s + d. diamonds. queen.4. 3. and lubs. So for example. A number is said to be perfe t if it is equal to the sum of all numbers whi h are its fa tors (ex luding itself).3. 7.Q. your program should print \7 of diamonds". and a e are respe tively assigned the numbers 11.rst step in su h a program would be to represent ards using numbers. The 13 ards of ea h suit have the denomination 2.K. Write a program whi h prints all the prime numbers smaller than n. The denominations 2 { 10 are assigned numbers same as the denomination. In a standard de k. Can you write the program to determine if a number is prime without using a bool variable? Hint: ount how many fa tors the number has. Suppose you want to add two 64 bit (unsigned) numbers.1. be ause it is the sum of its fa tors 1. and the spade king the highest. It is natural to assign the numbers 3. 6 is perfe t. Here is how you ould do it. hearts.A. there are 52 ards. Write a program whi h determines if a number is perfe t. Write a program whi h takes a number and prints out what ard it is. 12. 8.5. 13 of ea h suite. There are 4 suites: spades.

ant 32 bits in an unsigned int variable. and the more signi.

and ea h variable storing one digit (whi h has 64 bits) in ea h 32 . ant 32 bits in another unsigned int variable. This is equivalent to representing the number using the radix 2 .

81

Abhiram Ranade, 2011. Do not distribute

long variable. Suppose now that we have stored the most and least signi

ant bits

of the

**rst number in variables ams32 and als32, and similarly the se
ond number
**

in variables bms32 and bls64. Say we want to get the sum in variables
ms64 and

ls64. We
an obtain the least signi

**ant 32 bits merely by writing
sls32 = als32
**

+ bls32; { however we also need the
arry out of the least signi

**ant 32 bits. What
**

ondition will you
he
k to determine what the
arry will be? Note that if you do

arithmeti
on 32 bit integers, you basi
ally get the result modulo 2 .

How would you multiply two 64-bit numbers? Hint: If a,b are unsigned short and

is unsigned int, then
=a*b will indeed get the 32 bit produ
t of a,b into
.

Make an animation of a ball boun
ing inside a re
tangular box. Assume for simpli
ity

that the ball has an elasti
ollision with the walls of the box, i.e. the velo
ity of the

ball parallel to the wall does not
hange, but the velo
ity perpendi
ular to the wall

gets negated. Put the pen of the ball down so that it tra
es its path as it moves. You

an either read the ball position and velo
ity from the keyboard, or you
an take it

from
li
ks on the
anvas. Move the ball slowly along its path so that the animation

looks ni
e.

Modify the animation assuming that the box has mass equal to the ball, and is free to

move. Give an equal and opposite velo
ity to the box and the ball so that the
enter of

mass of the system does not move, and thus stays in the s
reen. Note that now in ea
h

ollision the velo
ity of the box will also
hange. This problem is mu
h harder than

the previous one, sin
e the box will start rotating on
ollisions. For simpli
ity assume

that there is something that prevents rotations, and linear momentum is
onserved.

A digital
ir
uit takes as input ele
tri
al signals representing binary values and pro
esses them to generate some required values, again represented as ele
tri
al signals.

As dis
ussed in Se
tion 2.2, a
ommon
onvention is to have a high voltage value (e.g.

0.7 volts) represent 1, and a low value (e.g. 0 volts) represent a 0. A digital
ir
uit is

made out of
omponents
ustomarily
alled gates. An AND gate has two inputs and

one output. The
ir
uit in an AND gate is su
h that the output is 1 (i.e voltage at

least 0.7 volts) if both inputs are 1. If any input is a 0 (i.e. voltage 0 volts or less),

then the output is a 0. Likewise, an OR gate also has 2 inputs and a single output.

The output is a 0 if both inputs are 0, and it is one if even one of the inputs is a 1.

An XOR gate has 2 inputs and one output, and the output is 0 i the inputs are both

the same value. Finally, a NOT gate has one input and one output, and the output is

1 if the input is 0, and 0 if the input is 1.

Figure 5.1 shows the symbols for the NOT gate, the AND gate and the OR gate at

the top, left to right, and a
ir
uit built using these gates at the bottom.

The inputs to a digital
ir
uit are drawn on the left side, and the outputs on the right.

The gates are pla
ed in between. A gate input must either be
onne
ted a
ir
uit input

or to the output of some gate to its left. The gate input takes the same value as the

ir
uit input or the output to whi
h it is
onne
ted. In the

**gure, a; b;
are the
ir
uit
**

inputs. Some gate outputs are designated as
ir
uit outputs, e.g. outputs p; q. Note

32

11.

12.

13.

14.

82

Abhiram Ranade, 2011. Do not distribute

a

c

d

b

**Figure 5.1: Cir
uit
omponents and a
ir
uit
**

that if two wires in the
ir
uit
ross, then they are not deemed to be
onne
ted unless

a solid dot is present at the interse
tion.

In this exer
ise, you are to write a program whi
h takes as inputs the values of the

ir
uit inputs a; b, and prints out the values of the outputs
; d.

15. Develop a mini drawing program as follows. Your program should have buttons
alled

\Line" and \Cir
le" whi
h a user
an
li
k to draw a line or a
ir
le. After a user
li
ks

on \Line", you should take the next two
li
ks to mean the endpoints of the line, and

so after that a line should be drawn
onne
ting those points. For now, you will have

to imprint that line on the
anvas. Similarly, after
li
king \Cir
le" the next point

should be taken as the
enter, and the next point as a point on the
ir
umferen
e. You

an also have buttons for
olours, whi
h
an be used to sele
t the
olour before
li
king

on \Line" or \Cir
le".

there is no ni e way in whi h the above program an be written. the program should print the average mark obtained by the students and stop.Chapter 6 Loops Consider the following mark averaging problem: From the keyboard. in whi h the number of times to repeat must be spe i. but the number of repetitions equals the number of students. The marks are known to be in the range 0 to 100. but merely a signal that all the marks have been entered. Upon reading 200. So we annot use the repeat statement. If the number 200 is entered. and we dont know that before starting on the repetitions. The number of students is not told expli itly. ea h denoting the marks obtained by students in a lass. It might seem that the program requires us to do something repeatedly. Using the statements you have learned so far. it is not to be onsidered the marks of any student. read in a sequen e of numbers.

The repeat statement is not really a part of C++. but something we added through the pa kage simple pp be ause we didnt want to onfuse you with while and for in the very . and often more learly. We will also learn the for loop statement.ed before the exe ution of the statement starts. All the programs you have written earlier using the repeat statement an be written using while and for instead. In this hapter we will learn the while loop statement whi h will allow us to write the program des ribed above. whi h is a generalized version of the while statement.

But having understood these more omplex statements you will .rst hapter.

1. The ondition is evaluated.nd no real need for the repeat statement. in luding a blo k statement. 83 . and body is a statement.1 The while statement The most ommon form of the while statement is as follows. The while statement exe utes as follows. So we will dis ontinue its use from the next hapter. 6. while ( ondition) body where ondition is a boolean expression.

As you an perhaps already see. Su h pi tures are alled ow harts. When this happens. 84 Abhiram Ranade. Then we move on to exe ute the statement following the while statement in the program. But before we look at that let us take a few simple examples. just as it was for the repeat. So there are two outgoing arrows from the diamond ontaining the ondition. The arrows show whi h statement is to be exe uted next. Do not distribute Previous statement in the program False Condition True Body Next statement in the program Figure 6.1. after evaluating the ondition. 4. If the ondition is true. As des ribed. then the exe ution of the statement is omplete without doing anything more. then the body is exe uted. This is shown pi torially in Figure 6.1: While statement exe ution 2. sometimes des ribed as \if the ondition fails". and then step 2 will ause the exe ution of the statement to terminate. 3. main(){ . 2011. Here is a program to print out a table of the ubes of numbers from 1 to 100. Note that typi ally ea h iteration might hange the values of some of the variables so that eventually ondition will be ome false. Ea h exe ution of the body is alled an iteration. either the body is exe uted or we go to the next statement after the loop. Then we start again from step 1 above. If the ondition is false. this statement is useful for our marks averaging problem. it will be dete ted in the subsequent exe ution of step 1.

The exe ution will start by setting i to 1. Do not distribute } 85 int i=1. The . Abhiram Ranade. i = i + 1. while(i <= 100){ out << ``The ube of `` << i << `` is `` << i*i*i << endl. 2011. Sin e it is. we enter the body. Then we he k whether i is smaller than or equal to 100. } out << ``Done!'' << endl.

Again we dis over that the urrent value of i. and whi h we keep on in rementing. 2. Thus we print \Done!" and stop. is smaller than or equal to 100. We again exe ute the statement i = i + 1.y) whi h will return xy .1.rst statement in the body auses us to print \The ube of 1 is 1". In other words. this time with i=2. so what gets printed is \The ube of 2 is 8". In this way it ontinues. and so we go to the statement following the loop. . and try out su essive values of d until we get to a d su h that 10d > n. How long should we in rement? We are to stop as soon as d attains a value d su h that 10d > n. But before this we have exe uted the loop body for all values of i from 1 to 100. Then we in rement i. we should not stop while 10d n. Computing 10d turns out to be easy in C++. ausing i to be ome 3. main(){ int n. The number of digits in a number n is simply the smallest positive integer d su h that 10d > n. So our program ould merely start at d = 1. When i be omes 101. } } // pow(a. Generating su essive values. In other words. in >> n. So we print again." << endl.d)){ d = d + 1. while(n >= pow(10. we exe ute iterations of the loop until (and in luding) i be omes 100.. until i is no longer smaller than or equal to 100. the ondition i >= 100 fails. We then go ba k and repeat everything from the ondition he k.0. out << "Type a number: ". int d = 1. Thus we will have printed the ube of all the numbers from 1 to 100.b) = a raised to b out << "The number has " << d << " digits. This is what the following ode does. and he k the ondition again. 6. be ause i has value 1. be ause of a ommand pow(x.1 Counting the number of digits We onsider one more problem: read in a non-negative integer from the keyboard and print the number of digits in it. After that we go ba k to the top of the statement. starting from 1 is also easy: we have a variable d whi h we initialize to 1.

Say in response to the request to type in a number. 2011. Do not distribute Let us see what happens when we run the program. 86 Abhiram Ranade. Then we would set d to 1. Then we would ome to the while loop. We would . we entered 27.

nd that n. So we enter the loop. Inside the loop. We then go ba k to the beginning of the loop and he k the ondition. whi h equals 27 is indeed bigger than or equal to pow(10.d) whi h equals 10 be ause d equals 1. we add 1 to d so that it be omes 2. This time we would .0.

2) whose values is 100.1.2 Developing loop based programs When developing loop based programs. Following that we dis uss the mark averaging problem.2.2. as the number of digits. Se ond. 6. This is the orre t answer: the number of digits in 27 is indeed 2. where i is any natural number. Thus we would print the urrent value of d. whi h is 2. The negation of this ondition will be ome the ondition in the while statement. i. this may require some adjustment. Finally. In this se tion we start by developing the program for the problem of Hema handra numbers. de. and of ourse more examples. we have to organize our ode so that we an reuse the variables going from one iteration to the next. First.e.2. So we do not enter the loop but instead go to the statement following the loop. the body of the loop must prepare the variables for being used again in the next iteration as needed.0. ea h iteration of the loop will a ess the same variables. 6. In the following se tions we onsider variations of the while statement and the for statement. As we will see in Se tion 6. we must identify the pattern of repetitive a tions. This is sometimes tri ky. there are 3 main issues to worry about. we must identify the ondition under whi h the repetition should be stopped.2. as will be seen in Se tion 6. These a tions will go into the body of the loop.1 Hema handra numbers Consider a sequen e Hi.nd that n whose value is 27 is smaller than pow(10.

ned as follows. 8 if i = 1 < 1 Hi = 2 if i = 2 : Hi + Hi if i > 2 This de.

in general in a re urren e the ith term of a sequen e is de.nition of Hi is said to be a re urren e.

The ases dire tly de.ned using the pre eding terms.

and there need to be n 2 iterations. we an ompute H using the re urren e and base ases: H = H + H = 2+1 = 3. For now we will onsider how to ompute its elements. H were omputed before entering the loop. How this sequen e arises is dis ussed later in Se tion 10. So presumably a loop will be useful to program it. Clearly. there is something repetitive going on here. After that we an ompute H = H + H = 3+2 = 5. and this pro ess an go on. Clearly. we an ompute one Hema handra number in ea h iteration. Presumably. but for larger values of i.ned. H are known immediately.3. H . be ause H . are said to be the base ases. we need to do some work. After that we an ompute H . H above. How do we ompute the nth Hema handra number Hn? H . 1 2 1 2 1 3 3 4 3 2 2 1 5 1 2 2 .

and whi h we will add to produ e a value whi h will be pla ed in a variable urrent. Do not distribute $H_1=1$ $H_2=2$ second last (a) $H_3=3$ $H_4$ current last + $H_1=1$ $H_2=2$ $H_3=3$ second last (b) $H_4$ $H_5$ last current + Figure 6.2. last=h2. Similarly. h2 = H_2 // prepare for next iteration out << urrent << endl. So here is the possible program. The key point. whi h we will assume already have values. // Program to ompute Hema handra number H_n int h1=1.2 our notion of what is last and se ond last must hange. if(n == 1) out << h1 << endl. and the se ond last iteration. repeat(n-2){ urrent = se ondlast + last. as shown in Figure 6. Figure 6. Figure 6. main(){ int n. So a ordingly we hange their values.h2=2.2(b).2: Computing Hema handra Numbers To al ulate a number in the urrent iteration. in >> n. In the ode. however. 2011. we need to add the numbers al ulated in the last iteration. else { int se ondlast=h1. This is the body of the loop. last. the \ urrent" of Figure 6. as shown in Figure 6. is that what is \last" in one iteration. last = urrent.2(a) is alled \se ond last" in the next iteration. We have to keep this in mind while writing the ode. we will have variables se ondlast. .2(b). else if(n == 2) out << h2 << endl. 87 Abhiram Ranade. To go to the next iteration. // h1 = H_1. whi h must be exe uted n 2 times.g. e.2(a) be omes \last" of Figure 6. urrent. } } } se ondlast = last.

last = urrent. but in the urrent problem. Do not distribute The important point to note in this example is the preparation of the variables se ondlast and last for the next iteration. while(i < n-2){ urrent = se ondlast + last. i++.2 Mark averaging This problem. we have to only print out their average. holding the last omputed Hema handra number. 6. This also stresses the important point that we should onsider ea h variable as performing a ertain fun tion. By that we mean that the omputer re eives a stream (sequen e) of values. is what we might all a data streaming problem. else if(n == 2) out << h2 << endl. h2 = H_2 // prepare for next iteration out << urrent << endl. we know what we want at the end: we want to print out the average.g. O asionally. // Program to ompute Hema handra number H_n int h1=1. e. in >> n. and how they should be updated. and we are expe ted to produ e something when the stream terminates.2. we may be expe ted to print out a stream of values as well. } } } se ondlast = last. if(n == 1) out << h1 << endl. and a ount of how many values we read. // h1 = H_1. We dont need to remember all marks that we have read so far! So it would seem that we should keep a variable sum in whi h we maintain the sum of the values that we have read till any point in time. 88 Abhiram Ranade. We will have a repeated portion in whi h . So at an intermediate point in the program. like many problems you will see later. We should also maintain a variable ount whi h should ontain the number of values we read. when some n values have been read. To al ulate the average we need to know the sum of all the values that we read. last=h2. and the value of the variable must be hanged to re e t its fun tion. else { int se ondlast=h1. A general strategy for ta kling su h problems is to ask yourself: what information do I need to remember at a point in exe ution when some n values of the stream have been read? The answer to this often suggests what variables are needed. We an of ourse rewrite this as a while loop.h2=2. For the mark averaging problem. int i=0. 2011. we should keep tra k of n as well as their sum. main(){ int n. urrent. Both variables should start o 0.

If nextmark is 200. and for this we will have a variable alled nextmark. Using these it would seem that we need to do the following steps repeatedly. 2011. 1. 89 Abhiram Ranade. then we have . Do not distribute we read a value. Read a value into nextmark. 2.

In Figure 6. It seems natural to mat h the ondition in the former with the test nextmark == 200 in the latter. and also in rement ount. If nextmark is not 200. But there is an important dieren e in the stru ture of the two ow harts.1 and Figure 6.2(a). you would need to mat h the pattern of the ow harts of Figure 6. and so we go on to al ulating and printing the average. But that is simply dividing sum by ount. then we add nextmark to sum. In this we have not written down the pro ess of al ulating the average et . 3. We repeat the whole pro ess from step 1. Can we express this ow hart using the while statement? For this.1 the ondition test is the .2.nished reading. 4. Figure 6.2.2(a) shows this as a ow hart.

2(a).rst statement of ea h iteration. the .2. while in Figure 6.

. Thus we an write our ode as follows. } } in >> nextmark. We do not want to hange what happens on ea h bran h that enters P.2(b)) // Box B // Box B // left opy of box A (Figure 5. and box C the ondition. This gives us the ow hart of Figure 6.rst statement is reading the data. but the new ow hart mat hes the pattern of Figure 6.2(b)) out << ``The average is: `` << sum/ ount << endl. This new box an be ome the body of a while statement. the two ow harts are equivalent in that they will ause the same statements to be exe uted no matter what input is supplied from the keyboard.2(b). sum=0. The ru ial question then is: an we somehow modify the ow hart of Figure 6. A (left opy) in Figure 6. main(){ float nextmark.1? Suppose we de ide to move the box labelled A upwards above the point P where two bran hes merge. int ount=0. ount = ount + 1. so we an even merge them into a single box ontaining 3 statements.2.2. and only the se ond statement is the ondition he k. so then it simply means that we must pla e a opy of A on both bran hes oming into P.2(b) are exe uted su essively. (Figure 5. Note now that the boxes B. // right opy of box A while(nextmark != 200){ sum = sum + nextmark.2(a) so that the exe ution remains the same.2. in >> nextmark. As you an see.

sum = sum + nextmark.3: Flow harts for averaging . count = count + 1. 2011. count = count + 1. C C nextmark == 200 B nextmark == 200 B sum = sum + nextmark. Do not distribute Start Start A A cin >> nextmark. P P A cin >> nextmark. cin >> nextmark. 90 Abhiram Ranade. Statement to calculate and print average (a) Original flowchart Statement to calculate and print average (b) Equivalent flowchart Figure 6.

statement to be used inside the body of a while (both forms). } out << total/nmarks. we an get the test to be at the top by moving around some ode and also making a opy of it.3 The break statement C++ allows a break. so that ount will not be zero at the end. sum=0. In su h ases. Do not distribute 91 The above program assumes that there will be at least one true mark. sum = sum + nextmark. If this happens. ount = ount + 1. while(true){ in >> nextmark. 6. int ount=0. 2011. Soon you will start doing this automati ally. Note the general idea arefully: the natural way of expressing our program ould involve a test in the middle of the ode we wish to repeat. if(nextmark == 200) break. Abhiram Ranade. The break statement auses the exe ution of the ontaining while statement to terminate immediately. exe ution is said to have broken out of the loop. The . Here is a dierent way of writing our mark averaging program using the break statement: float nextmark.

In general it is a good idea to not dupli ate ode. suppose you later de ide that just as you read mark you also want to print what was read. but more importantly it prevents possible errors that might arise later. First. For example. After the nextmark is read.2. Is the new program better than the old one? It is better in one sense: the statement in >> nextmark. and we move on to the next statement.2(a). this keeps the program small. The old ode was better in that the ondition for terminating the loop was given up front. the statement does terminate be ause of the break statement in the body. In the new ode. So in this sense the new ode is more natural. at the top. the reader needs to sear h a little to see why the loop will not exe ute ad in. If the nextmark is not 200. whi h prints out the average. we add nextmark to sum and so on. then you might forget to make the hange in all the pla es. Note that this is similar to the ow hart of Figure 6. as it appears in the old ode. This means that the statement will potentially never terminate! However.rst point to note here is that ondition is given as true. it is he ked for equality with 200 { if so the statement terminates immediately. is written only on e. Then if the reading ode is in several pla es. The result of this exe ution will be the same as before. rather than pro ess-read. You may also think that the basi repetitive unit of work in the problem is read-pro ess.

nitum. Unfortunately there is no one orre t answer. .

The exe ution skips the rest of the loop body but does go ba k to the beginning of the loop and start the next iteration (in ontrast to break whi h would terminate and not start the next iteration). then we begin again from step 1. It is written slightly dierently. if(nextmark < 0){ out << ``Negative number.4 The ontinue statement What if someone typed in a negative number for nextmark? Usually marks are expe ted to be non-negative. If the body evaluates to false then the exe ution of the statement ends. sum = sum + nextmark. In other words.5 The do while statement The while statement has a variation in whi h the ondition is tested at the end of the iteration rather than at the beginning. 2011. 2. ontinue. but he k if the value given is reasonable. This is exe uted as follows. If you know this for sure. This is pre isely what happens if you in lude a ontinue statement in the body. The form is: do body while ( ondition). The body is exe uted. Abhiram Ranade. the body is exe uted at least on e. } 6. In this ase you might want to simply print a message. The ondition is evaluated.'' << endl. then very likely the person who was typing made an error. in the do-while form. Do not distribute 92 6. and ignore the rest of the body. Thus we might write the last while loop as: while(true){ in >> nextmark. It is a good idea to not blindly a ept everything that is typed. ignoring. If it evaluates to true. the new form is more ompa t if you dont want the ondition he ked for the . 1. } if(nextmark == 200) break. You will observe that the do-while form above is equivalent to the following ode using only the while: body while ( ondition) body So you may wonder: why do we have this extra form as well? As you an see. ount = ount + 1.

rst iteration. Here is a typi al example. .

we an express the above ode as follows. do{ out << ``Type the number whose square root you want: ``. i hanges from one iteration of the loop to another in a very uniform manner. i <= 100. i = . Be ause of this. You would solve this problem using the following pie e of ode. in rement) body In this. This general ode pattern: that there is a ertain variable whi h takes a dierent value in ea h iteration and the value determines how the iteration will exe ute. out << ``The square root is: `` << sqrt(x) << endl. for(int i=1. the designers of C++ (and other programming languages) have provided a me hanism for expressing this pattern very ompa tly.6 The for statement Suppose you want to print a table of ubes of the integers from 1 to 100. ex ept for the value of i.g. } The variable i plays a entral role in this ode. int i = 1. Abhiram Ranade. } out << ``Type y to repeat: ``. This will keep printing square roots as long as you want. This me hanism is the for statement. 2011. but for mu h of the book we will assume that initialization and in rement are assignments to a variable but without in luding the semi olon. Using the for statement. Do not distribute 93 main(){ float x. All iterations of the repeat are identi al. in >> response. in the above ase it is in remented by 1 at the end of ea h iteration. in >> x. is very ommon. 6. initialization and in rement are required to be expressions. ondition . e. i = i + 1. repeat(100){ out << i << `` `` << i*i*i << endl. Expressions are dis ussed in Appendix ??. Further. This ode is equivalent to the repeat loop above. Exa tly why this is the ase will be ome apparent when we understand the for statement in its general form: for(initialization . } while(response == 'y'). har response. i = i + 1) out << i << `` `` << i*i*i << endl.

Abhiram Ranade. Further we may in lude the de. 2011. Do not distribute 94 i + 1.

As you might expe t ondition must be a boolean expression. The exe ution of a for statement is best spe i.g.nition along with the assignment e. in luding a blo k statement. The last part. int i = 0. body may be any C++ statement. Note that body will in lude a termination semi olon inside it if it is a single statement.

for dierent values of the ontrol variable. The variable named in initialization and in rement is ustomarily alled the ontrol variable of the loop. the in rement indeed adds 1 to the ontrol variable. and the in rement says how the variable must hange from one iteration to the next.6. As you an see.'' be ause it is not a part of // ``initialization''. We repeat this pro ess again starting from evaluation of ondition. in rement. this part of the for statement is alled the in rement. while( ondition){ body // we did not put the ``. If ondition is false. } In other words. You probably also see why the statement is alled a for statement. If the ondition is true. our for statement exe ution starts with the exe ution of initialization. Then ondition is evaluated.'' be ause it is a part of ``body''. the ontrol variable ould be de. then the statement terminates.ed in terms of a while statement. As you might expe t. the statements in the body are exe uted followed by the in rement. It is be ause we exe ute the body many times. in our ube table example. // we put the ``. initialization. 6. Thus the for statement above is the same as the following sequen e of statements.1 Use of the ontrol variable outside the for As we mentioned. Sin e this happens often. initialization assigns an initial value to the ontrol variable.

the for statement is said to be the s ope of the ontrol variable. the ontrol variable an be used only within the for statement. then the ontrol variable should be de.nition inside initialization. but not referred to outside the for. In this ase. If the value of the ontrol variable is useful after the for exe ution is over. as in our ube-table program. In su h ases.

and only initialized in initialization.ned outside the for statement. it is best to de. In su h ases. Very often. the ontrol variable is not of use outside the for statement.

What if I de.ne it within the initialization to avoid lutter and keep related information together.

but an i has already been de.ne a variable i in initialization.

for(int i=1. i = i + 1) out << i*i*i << endl. out << i << endl.ned earlier? So onsider the following ode. i<=100. . int i=10.

Do not distribute 95 In this ase the i de. 2011. Abhiram Ranade.

ned in the .

rst statement will be dierent from the one de.

but it will be the same as the one in the last statement! Thus the for statement will print a table of ubes as before.ned in the for statement. The last statement will print 10. whi h is the value of the variable (de.

ned in statement 1 and un hanged by statement 2) it refers to. the de. In su h ases.

ned in statement 2 is said to shadow the de.

I an hoose any name I want for it and de. When I start writing the for statement.nition in statement 1. However the shadowing is operative only while statement 2 is being exe uted. There is a reason for this seeming madness as well. if I know that my ontrol variable is not needed outside.

ne it in the initialization. 6. The name used in the for statement will not interfere with the names outside. then the exe ution of the for statement . I dont need to worry whether the name has been used earlier in the program.6.2 Break and ontinue If a break statement is en ountered during the exe ution of body.

but also for use by others. when I write a for statement. otherwise you will yourself have diÆ ulty understanding why you wrote something! 6. it is possible that you will perhaps use it again after a few months or years. Hen e it is important to write it so that its logi is understood by others as easily as possible. Likewise. you will want it well written. starting with he king ondition and so on. and then the next iteration is exe uted.3 Style issue You may well ask: why should we learn a new statement if it is really not needed? The reason is mu h the same as why we speak loudly on ertain o asions and softly on others.4 Primality In Se tion 5. The in rement is exe uted. is to try to . then the exe ution of the urrent iteration is terminated. The basi idea. as before.2 we saw one way of determining whether a number is prime. If I use either a while statement or a repeat statement. We will improve upon that in two ways.6. At that point. 6.nishes. our softness/loudness help the listener understand our intent in addition to our words. it is very lear to the reader that I am using a ertain ommon programming idiom in whi h there is a ontrol variable whi h is initialized at the beginning and in remented at the end of ea h iteration. Even if you feel that no one else will read your program.6. Do note that in the modern era the program you write is not only for exe ution. If the ontinue is en ountered.6. then the reader does not immediately see all this.

x.nd a fa tor of the given number. If we .

If however.nd fa tor. we do not . we an immediately stop sear hing further (by using break) and on lude that the number is omposite.

How many dierent andidates should we onsider as possible fa tors of x? In Se tion 5.2 we onsidered all integers from 2 to n 1. But this is too many. then we an on lude that the number is prime. If some y is a .6.nd a fa tor but have tried all possibilities.

break. i. n=y annot be larger than n. Thus to he k whether n has anypfa tors. int x. 6. Do not distribute p fa tor of n. Thus we must have p at least one fa tor no larger than n. But this is not a problem. that we do not know n. then so is n=y. But both y. This immediately gives us the program. 96 Abhiram Ranade. for(int y=2. in >> x. } } if(found) out << "Composite. be ause we an express the se ond ondition as y y n. integers y p su h that 2 y n. it suÆ es to he k only the integers between starting at 2 going up top at most n.e.5 Natural log by numeri al integration The natural logarithm of a number x is de.\n".\n". else out << "Prime. y*y<=n. 2011. Note however.6. bool found = false. i++){ if(x % y == 0){ found = true.

ned as y su h that ey = x where e is Euler's number (e 2:71828). We onsider the how to ompute y de.

ned above given x. we will use an alternate relationship: Z x 1 du y= u In other words. So we an . y = ln x is the area under the urve y = 1=u between u = 1 and u = x. For the omputation. There are various ways of doing this. we will hoose one of the simplest ways.

nd ln x if we an .

In general suppose we wish to approximate the area under a urve f (u) = 1=u from some p to q. The height of this re tangle is f (p) (be ause f is non-in reasing) and the width is q p. after dividing the required area into n verti al strips. Then we an get an overestimate to this area by onsidering the area of the smallest axes parallel re tangle that overs it. We will take ea h su essive term of the series and add it into a variable area whi h we . we annot ompute the area exa tly. but we an approximate it.nd the area! Well. Sin e the urve goes from 1 to x the width of ea h strip is w = (x 1)=n. The height of the re tangle overing this strip is f (1+(i 1)w) and hen e the area is wf (1+(i 1)w). The ith strip extends from u = 1 + (i 1)w to u = 1 + iw. Thus the total area of the re tangles is: n n X X 1 w wf (1 + (i 1)w) = 1 + (i 1)w i i But evaluation of this formula is easily translated into a program! In fa t i will naturally serve as a ontrol variable for our for loop. This is the strategy we will use. Thus our required approximation (over estimate) is (q p)f (p).

1 =1 =1 . The following is the omplete program.rst set to 0.

If you use this ommand in your ode. It is worth pointing out that there are two kinds of errors in a omputation su h as the one above. The . so you will be guaranteed to get a result whi h is orre t to as many bits as your representation has (more a urate for double than for float). the ode will be a bit more sophisti ated. Do not distribute main(){ float x. w. out << ": ln(" << x << ") = "<< area << endl. Only. 97 Abhiram Ranade. i = i+1) area = area + w * (1/(1+(i-1)*w)). then some ode like what we have developed above will get used. before the end of the program given above. But we an use the C++ supplied ommand to he k how good our answer is. 2011. To do this simply add the line log(x) out << "ln(" << x << ") = "<< log(x) << endl. } We note that C++ already provides you a single ommand log whi h an be invoked as and it returns the value of the natural logarithm. in >> x. int n. i<= n. area=0. w = (x-1)/n. for(int i=1. in >> n.

For the natural log. this orresponds to the error that arises be ause of approximating the area under the urve by the area of the re tangles. The se ond kind of error arises be ause on a omputer numbers are represented only to a . This error will redu e as we in rease n. the number of re tangles.rst is the error produ ed by the mathemati al approximation we use to al ulate a ertain quantity.

it is possible to show that the error will be proportional to pn. we will have error be ause our al ulation of the area of ea h re tangle will itself not be exa t. assuming all errors were in the same dire tion. we should hoose n large. Thus. The exer ises ask you to experiment to . In other words. If we use float representation then every number is orre t only to a pre ision of about 7 digits. ea h with an error of about 10 .xed pre ision. if you add 10000 numbers. then the error in the sum ould be ome n. Thus. your total error is likely to have risen to about 10 (if not to 10 ). If you add n numbers ea h ontaining an (additive) error of . Even assuming that the errors are random. but not too large.

Later we will see other methods of omputing mathemati al fun tions (in luding the natural log) whi h will be based on ompletely dierent ideas.nd a good hoi e. This method. 7 5 6. The C++ supplied ommand log likely uses one of these other methods.6. and the more intriguing method based on Simpson's rule are left to the exer ises.6 Mark Averaging 3 We . Another variation on the method is to approximate the area under the urve by a sequen e of trapeziums. This indeed helps.

rst observe that the example from the previous se tion also .

ts well. Indeed that ode an also be written using a for statement as follows. .

sum + nextmark. Do not distribute 98 float nextmark.sum=0. nextmark != 200. Write a program that returns the approximate square root of a non-negative integer. Exer ises 1. float ount=0. I suspe t that some programmers will like this way of writing the program. Abhiram Ranade. 2011. in >> nextmark){ = ount + 1. for( in ount sum = } out << >> nextmark. sum/ ount. For this exer ise de.

'a'.e. Use this to ompute the natural logarithm. one at a time. 7. the string \abra adabra". Suppose some ode ontains some while statements. 'a'. Hint: What information do you need to have after reading ea h hara ter? Try to maintain that. ' '. 10. 'a'. This area is simply (f (p) + f (q))(q p)=2. Run the program to ompute natural logarithm and he k whether it gives better answers for higher values of n. 5. 2. 4. (q. 'r'. Write a program that omputes n! given n. A more a urate estimate of the area under the urve is to use trapeziums rather than re tangles.ne the approximate square root to be the largest integer smaller than the exa t square root. and says whether it ontains the sequen e of hara ters 'a'. Run the program for omputing natural log for various hoi es of n and see how the result varies. q℄ will be approximated by the area of the trapezium with orners (p. Write a program that prints a onversion table from Centigrade to Fahrenheit. (p. 8. f (p)). 3. 'r'. 6. Your are expe ted to not use the built-in sqrt ommand. 'b'. 'b'. For what value of n do you get an answer losest to the log fun tion of C++? 9. 0). 'a'. Show how you an repla e the while statements by for statements without hanging the output produ ed by the ode. of ourse. 'd'. Simpson's rule gives the following approximation of the area under the urve of a fun tion f : Z b b a a+b f (x)dx 6 f (a) + 4f 2 + f (b) a . Write a program that reads in a sequen e of hara ters. i. Thus the area under a urve f (u) in the interval [p. f (q)). Write a program that omputes xn given x and n. (q. 0).

14. Do not distribute 11. 12. 2011. 99 Abhiram Ranade. 15. 16. 18. 13. Use this rule for ea h strip to get another way to . 17.

(b) al ulate the area of the polygon. Suppose we are given n points in the plane: (x . and then use Heron's formula to . y ). Then ompute the lengths of the sides of the triangles. : : : . yn).nd the natural log. and are given in the ounter lo kwise dire tion around the polygon. Hint 1: Break the area into small triangles with known oordinates. Suppose the points are the verti es of a polygon. Write a program to (a) al ulate the perimeter of the polygon. (xn.

Hint 2: Break the boundary of the polygon into two parts. Modify the program so that it runs until the user li ks on the stop button. an up fa ing boundary and a down fa ing boundary. Express the area as the area under these boundaries ea h onsidered as fun tions f (u). Then add up.nd the area of the triangles. Write a program that prints out the digits of a number starting with the least signi.1.4. Add a \Stop" button to the turtle ontroller of Se tion 5.

going on to the most signi. ant digit.

Note that the least signi. ant.

: : : . Write a program that takes a natural number and prints out its prime fa tors. xj onsider its sum Sij . A natural number is said to be a palindrome if the sequen e its digits is the same whether read left to right or right to left. Hint: This is a diÆ ult problem. xn be a sequen e of integers (possibly negative). Write a program that takes a number n and prints out a number m whi h has the same digits as m. but in reverse order. with n given at the beginning. ant digit of a number n is simply n % 10. For ea h possible subsequen e xi . and prints out the maximum sum Sij over all possible subsequen es. Write a program that reads in the sequen e in order. Let x . Write a program that takes as input a natural number x and returns the smallest palindrome larger than x. Write a program to determine if a given number is a palindrome. it will yeild to the general strategy: . However. : : : .

gure out what set of values V (k) we need to remember having seen the .

rst k numbers. 1 1 1 . you must ompute V (k + 1) using the number read and V (k) whi h you omputed earlier. When you read the k + 1th number.

exponentials and logarithms. We will also see how to ompute the greatest ommon divisor of two numbers using Eu lid's algorithm. invented well before omputers were even on eived. The main statement in all the programs of the hapter will be a looping statement. 7. You ould onsider this hapter to be an extension of the previous. Some of the material in this hapter requires somewhat deep mathemati s. The pre ise proofs are outside the s ope of this book.1 Taylor series Suppose we wish to ompute f (x) for some fun tion f . and try to explain intuitively why they might be true. su h as trigonometri fun tions. We will state the relevant theorems. This is one of the oldest interesting algorithm. giving more ways in whi h loop statements an be used.Chapter 7 Computing ommon mathemati al fun tions In this hapter we will see ways to ompute some ommon mathemati al fun tions. Suppose we know how to ompute f (x ) for some . square roots. su h as say f (x) = sin(x).

and we an evaluate these. Then if x is reasonably lose to x then f (x) equals the sum of the Taylor series of f at x . we only ompute and sum the . in whi h f i0 is the fun tion obtained from f by taking derivative i times. Suppose that the derivative f 0 of f and the derivative f 00 of f 0 and so on exist at x . Thus we have: (x x ) + f 000(x ) (x x ) + f (x) = f (x ) + f 0 (x )(x x ) + f 00 (x ) 2! 3! In the typi al s enario.xed x . The ith term of the Taylor series is f i0(x )(x x )i=i!.

you may re ognize the .rst few terms of the series. However. The general theory of this is dis ussed in standard mathemati s texts and is outside our s ope. and that gives us a good enough estimate of f (x).

as shown in Figure 7.rst two terms as oming from a tangent approximation of the urve. whi h in turn is FB + BC = EA + (BC/AB)AB = f (x ) + f 0(x ) (x x ). We approximate this by FC.1. The value of f (x) equals (the length of) FD. 0 0 0 0 0 0 0 0 0 0 0 0 0 0 100 0 2 0 0 3 .

Then hoosing x = 0 we know f (x ) = 0. 101 Abhiram Ranade. Do not distribute f Tangent at A. Thus we get sin(x) = x x3! + x5! x7! + x9! Here the angle x is in radians. f (x )) 0 0 7. where x is in radians. We know that f 0(x) = os(x). When a series has alternating positive and negative terms. Sin e os(0) = 1. 2011. and the terms get loser and loser to 0 for any . 1 or -1. onsider f (x) = sin(x). we know the exa t value of every derivative. f 000(x) = os(x) and so on.1. $(x_0.1 Sine of an angle As an example.1: Tangent to f at (x . it is either 0.f(x_0)$ D C A B E F $x_0$ $x$ Figure 7. f 00(x) = sin(x).

then it turns out that the error in taking just the .xed x.

We an al ulate the kth term tk from s rat h in the kth iteration. Clearly we will need a loop. but it is useful to note the following relationship: 0 0 3 +1 2 5 7 9 1 2 +1 = ( 1) x2k (2k 1 x2 1)! = tk ( 1) (2k 2)(2k 1) provided k > 1. So we are now ready to write a program. Thus our ode be omes: tk main(){ k +1 1 .rst k terms is at most the k + 1th term (absolute value). : : : as needed. If k = 1 then tk = 1. Thus within the loop we only ompute the terms for k = 2. in the kth iteration of whi h we will al ulate the series to k terms. 3. We must terminate the loop if the last added term is smaller than our target . of ourse. The kth term of our series is ( 1)k x k =(2k 1)!. Thus if we want the error to be then we should ensure x k =(2k + 1)! . and we dont use the above relationship.

Do not distribute double epsilon= 1.0E-20. 102 Abhiram Ranade. While writing the ode whi h adds up the elements of a series. double x. The ommand abs stands for absolute value. abs(term) > epsilon. it is useful to . 2011. k++){ // term must be t_{k-1} term *= -x * x /((2*k-2)*(2*k-1)). double sum=x. out << "x : ". double term = x. for(int k=2. sum += term. and returns the absolute value of its argument. // sum = sum of first k terms } } out << sum << endl. in >> x.

as we have shown. In fa t at the beginning of the fun tion. What are the values of the important variables (e.g. and de. term) supposed to be at the beginning or the end of the iteration? These de isions should be written down as omments. there should be a more detailed omment giving the series being used.rst de ide what ea h iteration is going to do.

1. 7.ning what tk is in that series. the natural logarithm of x. In the previous hapter we omputed this by .2 Natural log Consider f (x) = ln x.

Simply observe that ln x = 1 + ln xe . Thus by fa toring out powers of e we will need to use the series only on a number smaller than 1. 2 3 4 0 0 0 . Here we will use the Taylor series. Clearly f 0 (x) = 1=x. For the ln fun tion.nding the area under the urve 1=x. or equivalently x x = h is small. we have a pre ise des ription of what lose enough means: within a unit distan e from x . It is onvenient to use x = 1. f 00 (x) = 1=x and so on. Even so. note that you an indeed use the series to al ulate ln x for arbitrary values of x. We noted earlier that the Taylor series is valid only if x is lose enough to x . Thus we get: 2 0 ln1 + h = h h2 + h3 h4 A very important point to note for this series is that the series is valid only for 1 < h 1.

we have provided some intuitive justi. In fa t identities su h as sin(x) = sin( x) an be used to further redu e the value used in the main loop of the program. In fa t. suppose we wish to ompute sin(100:0). 2011. For example. However. Do not distribute 7.0 as input. it is best to keep x small if possible. Thus. The proof of the Taylor series expansion is well beyond the s ope of this book. noting that the Taylor series for os(x) is: f (x) = f (0) + f 0 (0)x + f 00 (0) 3 os(x) = 1 x2! + x4! x6! + we an in fa t ompute the sine using sin(x) = os(=2 x) if =2 x happens to be smaller in absolute value than x. sin e we know that sin(x + 2n) = sin(x) for any integer n.1. A better way is to subtra t as many multiples of 2 as possible. whi h is f (x0 + h) = f (x0 ) + f 0 (x0 )h + f 00 (x0 ) 3 0 0 x2 x + f 000 (0) + 2! 3! In general. One possibility is to use the previous program spe ifying 100. the terms of the Taylor series in rease with x.3 Some general remarks Note that the Taylor series is often written as h2 h + f 000 (x ) + 2! 3! If we hoose x = 0. 103 Abhiram Ranade. we get the M Laurin series.

ation for the .

2 Bise tion method for .1.rst two terms by onsidering the tangent to approximate the fun tion urve. 2 4 6 1 7. Figure 7.

a point where the plot of the fun tion tou hes the x axis. Many problems an be expressed as .nding roots A root of a fun tion f is a value x su h that f (x ) = 0. In other words.

nding the roots of an equation. For example. suppose we want to .

So .e. Then instead we ould ask for the rootspof the polynomial f (x) = x 2. x = 2 and this would give us the square root of 2.nd the square root of 2. i. if f (x) = 0 then we have x 2 = 0. Clearly.

In this se tion.nding roots is a very important mathemati al problem. we will see a very simple method for .

xR ℄. xR satisfy the onditions listed above. (or maximum error) in our knowledge of the root. The method will require that (a) we are given values xL xR su h that f (xL ) and f (xR ) have opposite signs. (b) f is ontinuous between xL and xR . = (0) and with this substitution the formula an be written as ( ) = (0) + (0) + (0) t2 . Getting a better approximation 0 0 2 2 2 2 You might be familiar with the formula ( ) = + 12 2.nding roots approximately. it must pass through zero somewhere in the ( losed) interval [xL. We an think of xR xL is the degree of un ertainty. and has opposite signs at xL. Be ause f is ontinuous. xR . Clearly xL . giving f (xR ) = 2. in whi h ( ) is the distan e overed in time by a parti le moving at a onstant a eleration . Note that2 = (0). whi h resembles the Taylor series in the . and xR = 2 (or any large enough value). with initial velo ity . for example for f (x ) = x 2 we an hoose xL = 0 giving f (xL) = 2. These are fairly minimal onditions.

rst 3 terms. 1 t s t ut at s t a u s t s s 0 u t s 00 s 0 a s 00 .

We ompute xM and . If the size of the interval is really small. we an return either endpoint as an approximate root. xL. 2011. So the main question is: an we somehow pi k better xL .f(x_R)$ $x_L$ $x_M$ $x_R$ Root $(x_M.e. xR su h that xR xL is smaller. Do not distribute $(x_R. Next we will have xL = xM .2: Bise tion method. Consider the interval midpoint: xM = (xL + xR )=2. xR given their urrent values.f(x_M)$ $(x_L. 104 Abhiram Ranade.f(x_L)$ Figure 7. i. A simple idea works. merely means getting a smaller interval.

Suppose the sign of f (xM ) is dierent from the sign of f (xL ). Then we would know that they are both at a distan e at most from the root. then it must be dierent from the sign of xR . sin e the root is inside the interval [xL . we have redu ed the size of the interval. The ode is then immediate. and thus redu ed our un ertainty. In that ase (see Figure 7. xR satisfy our original requirements. Indeed if we want to redu e our error to less than some . Clearly the new values xL . We write it below for . Then we know an set xR = xM . then we must repeat this pro ess until xR xL be omes smaller than . xR ℄. Again the new values of xL. Hen e in ea h ase. xR satisfy our 2 onditions.nd the sign of f (xM ). If the sign of xM is the same as the sign of xL.2) we set xL = xM .

i. 2 main(){ // find root of f(x) = x*x .nding the square root of 2. float xL=0. in >> epsilon. // invariant: f(xL).e.2.xR=2. bool xL_is_positive. xM_is_positive. float xM.2) > 0. for f (x) = x 2. xL_is_positive = (xL*xL .f(xR) have different signs.epsilon. .

2011. } while(xR-xL >= epsilon){ xM = (xL+xR)/2. if(xL_is_positive == xM_is_positive) xL = xM. Do not distribute 105 // Invariant: x_L_is_positive gives the sign of f(x_L).3 Newton Raphson Method We an get a faster method for . // does not upset any invariant! else xR = xM. 7. // does not upset any invariant! } out << xL << endl. Abhiram Ranade. xM_is_positive = (xM*xM -2) > 0.

assuming x x ur is small. In this equation we ould hoose x to be any point.3 shows what happens graphi ally. Our urrent andidate for the root is the point A. It is possible to argue that if A is lose to the root. The pro ess of omputing xnext given x ur is very intuitive. We know from Se tion 7. Or in other words. takes as input. a urrent andidate. and f 0(x ur ) = AB/AC = f (x ur )/AC. then Newton-Raphson gives mu h faster onvergen e to the root than the bise tion method. we repeat the method with xnext as the andidate. Otherwise.nding a root of a fun tion f if we an evaluate the derivative f . This method. if it is lose enough to 0. Thus we an get an approximation to the root! This approximation is what we take as our next andidate. Then f (x) = 0. then we report x urr as the root. in luding the root. but the proof is beyond the s ope of this book. Thus we have 0 = f (x ur ) + f 0(x ur ) (x x ur ).1 that f (x) f (x ur ) + f 0(x ur ) (x x ur ). say xnext. Noti e that the right hand side of this equation an be evaluated. Thus AB = f (x ur ). f (x ) xnext = 0 ur + x ur (7. It returns as output a (hopefully) better andidate. x f f0 xx + x ur . We now show how the Newton-Raphson method an be used to . due to Newton and Raphson. say x ur for the root.1) f (x ur ) That is all there is! Figure 7. So let us hoose x to be the root. We then ompute f (xnext ).

we must express the problem as that of .nd the square root of 2. As with the bise tion method.

and it is possible that with a bad hoi e the method will not get lose to the root at all! The standard idea is to make an approximate plot of the fun tion. Next we need an initial guess.nding the root of an equation: f (x) = x 2. So we will start with our initial guess x ur = 1:5. Choosing the initial guess is in general somewhat tri ky. But it turns out in this ase that other guesses will also work just . and hoose a point whi h appears lose to the root.

Ideally. The next input determines how lose we wish to get to the root. We give the ode next. ( ur ) ( ur ) 2 . whi h is read into the variable x ur. they may just take a few additional steps to get lose enough to the root.ne. The input to the program is the initial guess.

f(x_{cur})$ $x_{next}$ $x_{cur}$ Figure 7. So our program has another input. 2011.3: One step of Newton-Raphson p we should require that jx ur p 2j be smaller than some that we pprovide. In the main loop we .0001. This is not equivalent. we do not know 2. say 0. 106 Abhiram Ranade. Unfortunately. So we settle for something dierent: we try to ensure that jf (x ur )j = jx ur 2j < . but usually this gives us good results. whi h we read into the variable epsilon. and so we annot ompute jx ur 2j. Do not distribute B O R A C $x$ $(x_{cur}. .

2. out << "Give initial andidate: ". so we break out of the loop. and use this to ompute xnext . . xnext. in >> x ur. x ur = xnext. We next he k if jf (x ur )j < . out << "Give max allowed error in fun tion value: ". xnext = x ur . in >> epsilon. epsilon. Then we set x ur = xnext to prepare for the next iteration. if (abs(fx ur) < epsilon) break. Otherwise. while(true){ double fx ur = x ur*x ur . 2 main(){ double x ur.rst ompute f (x ur ) in the variable fx ur. If the test is true. then we have got lose enough. for this we use a built in fun tion abs provided in C++. we al ulate f 0 (x ur ) = 2x ur .fx ur/fdashx ur. double fdashx ur = 2*x ur.

We re ommend this oding style. Abhiram Ranade. But we have used them so that the logi is learer. 7. 2011.4 Greatest Common Divisor Suppose we wish to . Do not distribute 107 } } out << "The root is: "<< x ur << endl. Note that we do not really need separate variables su h as fdashx ur or even xnext.

nd the greatest ommon divisor of two integers m. Remember that the greatest ommon divisor (GCD) is the largest integer whi h divides both m. n. In primary s hools. you have doubtless learned how to . n.

nd the GCD: .

though a little mysterious. If the remainder is not 0. The algorithm. If the remainder is 0. i. Suppose we want to .e. It turns out that Eu lid's algorithm is mu h faster than the fa toring algorithm. Let us take an example.nd ommon fa tors. then the divisor at that stage is the GCD. then repeat the pro ess using the remainder and the smaller number. then the smaller number is the GCD. as taken from a standard X textbook of Mathemati s. invented by Eu lid long ago. and then take their produ t. It is also possible that you have learned another algorithm. Divide the larger number by the smaller. is as follows. divide the smaller number by the remainder and so on. At any point in this pro ess if the remainder be omes zero.

When 156 is divided by 36 we get 12 as the remainder. In a single iteration of the loop we will have two numbers to work on. so we stop and return the last divisor 12. the remainder is 0. We seem to be doing the same set of operations on dierent pairs of numbers. So we divide 192 by 156 and get 36 as the remainder.nd the GCD of 192 and 156. We . Large and Small. Indeed. When 36 is divided by 12. Say we use two variables. so learly the main part of the program will be a loop. The remainder is not 0. whi h will respe tively hold the larger and smaller of the two (doesnt matter if the numbers are equal). so we repeat with the smaller number 156 and the remainder 36. 12 is the GCD of the numbers 192 and 36. Sin e this not 0 we repeat with the smaller number 36 and the remainder 12.

rst .

when the Large is divided by Small. . and use a break after the test. We must be areful to pla e the larger of these into the variable Large. If the remainder is not 0. We an give it its value by writing Remainder = Large % Small. Note that at this point Then we must he k if the remainder is 0 { if so we have to stop the loop be ause we have found the GCD. Sin e the loop test is in the middle. but using the values of Small and Remainder this time. Can we tell whi h of these two is larger/smaller? We obtained Remainder by dividing by Smaller. Then we an go to the next iteration.nd the remainder. we know that the value in Remainder will be smaller than the value in Smaller. Sin e the remainder must always be smaller than the quotient. So we must assign the former to Small and the latter to Large. Clearly this will require some kind of a break statement. then we must repeat the pro ess. Suppose we use a variable Remainder to store the remainder. we will use a while loop with a true ondition. and the smaller in Small.

in>> Small. out << ``Enter the larger number: ''. } out << ``The GCD is: `` << Small. Our . This algorithm is a faithful implementation of the informal des ription given earlier. Large = Small. in >> Large. 2011. But an we prove it for ourselves? This algorithm is dierent from all the algorithms that you have studied so far in that it is not at all obvious that the break statement in the loop will ne essarily be exe uted. The previous algorithms were easy on this a ount. out << ``Enter the smaller number: ``. Abhiram Ranade. } while(true){ Remainder = Large % Small. Remainder. So if our lass X textbook is orre t. if (Remainder == 0) break. it should give the orre t answer. Small = Remainder. Do not distribute 108 main()(){ int Large. Small.

For the loop in the GCD problem. at least at . The previous uses of the while loop were easier. say there was a single variable i whi h was in reasing and the loop was repeated until the variable rea hed a ertain value.rst looping statement was the repeat in whi h the number of times to repeat was given at the beginning. no su h ondition an be seen.

and does not run for ever. So if n was the value of Small at the beginning. Thus before we worry about whether the algorithm gives the orre t answer.1 Proof of termination If you play around with the algorithm you will soon realize that the values of the numbers generally de rease. Small. Thus we know that Small must de rease in ea h iteration of the program. 7. Sin e Small is an integer. then there an be at most n iterations after whi h the value of Small has to be ome 0. Can we make a pre ise statement regarding this? Yes. we must make sure that it gives some answer.4.rst glan e. we have already argued that the value of Small in the next iteration is the value of Remainder in the urrent iteration. the de rease must be at least 1. So we have proved the . But the remainder must be smaller than the quotient.

it must stop sometime. We now prove that it prints the orre t answer. n be positive integers.2 Proof of orre tness Before stopping.rst part: our program annot run for ever. If m mod n 6= 0 then GCD(m. .4. n0 ) where m0 = n and n0 = m mod n. Theorem 1 (Eu lid) Let m. n) = n. n) = GCD(m0 . For this we need the following theorem. If m mod n = 0 then GCD(m. the algorithm will print an answer. 7.

2011. Abhiram Ranade. Thus m. Let g. g0 be the GCDs of m. Thus m + . n and m0 . Do not distribute 109 Let q be the quotient when m is divided by n. n are multiples of g. Thus we have m = qn + n0 . n0.

n must be a multiple of g for any integers . .

Hen e it an be no larger than their GCD. . i. n are the values of the variables Large. Small gets the value that Remainder has in this iteration. Clearly. g. n. i. m and n. Thus g0 = g. g 0 g . the values taken by Large and Small in the next iteration iteration. g0 g. This is the value of Small at the beginning of the next iteration as well.e. At the end of this iteration. Now n = m0 is learly a multiple of g0. Suppose m. n and m mod n will have the same GCD as the values they had in the urrent iteration. Thus m. n0 are multiples of g0.e. So by Eu lid's theorem. Large gets the value that Small has in this iteration. Now note that m0 . This is the value in Large at the beginning of the next iteration. n0 must be multiples of g. Be ause m0 = n. n are multiples of g 0 . This will happen in ea h iteration. we have that both m0. Thus n0 = m qn is also a multiple of g. Further m = qn + m0 = qm0 + n0 . So in every iteration the numbers we have in Large and Small will have the same GCD as they had in the very . Proof: Now onsider our program.e. What an we say about the values at the beginning of the next iteration? At the end of this iteration. So m is also a multiple of g 0 .Small at the beginning of some iteration. i. Thus the greatest ommond divisor g0 of m0 . n0 an be no smaller. this is m mod n.

e. Large % Small == 0. But under this ondition. Large must be a multiple of Small.e. i. But we have already shown that this must be the GCD of the values in the very . i. the algorithm orre tly prints out the GCD of the values of Large and Small in the last iteration.rst iteration. When the algorithm terminates we will know that the ondition for the break must be true.

rst iteration as well! 7.5 Summary This hapter has introdu ed several new ideas. We saw that if the fun tion and its derivatives are easy to evaluate for some values of the argument. then the Taylor series of the fun tion an often be used to give an algorithm that evaluates the fun tion for all values of the argument.1 Mathemati al ideas We saw some general te hniques for omputing mathemati al fun tions. We also saw that omputation of a fun tion f ould be expressed as the problem of .5. 7. though no new programming langauge features.

These methods require that we should be able to evaluate g and possibly its derivatives at arbitrary points.nding the roots of another fun tion g. Roots an often be found using various methods. .

2 Programming ideas The . 2011. Abhiram Ranade.5. Do not distribute 110 7.

they ould be al ulated from values al ulated in the pre eding iterations. The se ond important idea was that some properties of ertain variables may remain un hanged over the iterations of a loop. The notion of an invariant is important in reasoning about programs. Su h a property that remains the same at a given point in the loop is ommonly alled a loop invariant.rst idea was that the values required in ea h iteration of the loop need not be al ulated afresh. The . n) remained the same at the beginning of ea h iteration of the loop in our program. We saw for example that GCD(m. We saw the use of this idea in the al ulation of sin x.

and the sum ould never drop below zero. If we an argue that the potential must steadily drop but annot drop below a ertain limit. It is ustomary to refer to the sum as a potential fun tion for the loop. n had to de rease in ea h iteration of the loop.nal important idea is that of a potential fun tion. We argued that the GCD program must terminate be ause the sum of the values of m. then the only way this an happen is if the loop stops after a .

nite number of iterations. The name arises from Physi s. Write a program to . where ustomarily the parti les (or systems) have a tenden y to go from high potential (energy) to low. Exer ises 1.

One hild. Ashok. 2. Write down the Taylor series for f (x) = ex. onsider the Ma Laurin series. 3. Hint: ast it as a root . y as she wants. Children often play a guessing game as follows. Che k your answer by using the built in log ommand. pi ks a number between 1 and 1000 whi h he does not dis lose to another hild. Nutan asks questions of the form \Is you number between x and y?" where she an pi k x. Show that Nutan an guess the number orre tly using at most 10 questions. it is a good idea to use it on as small values of x as possible. noting that f i0(x) = ex. Write a program to ompute ex. however. It is onvenient to expand around x = 0. This series is valid for all values of x.nd ln x for arbitrary x using the Taylor series.e. Nutan. and he k against the built in ommand exp. i. Nutan's goal is to ask as few questions as possible and guess the number that Ashok pi ked.

m = mdash. ndash = n. What if the loop in the GCD program is 0 while(m % n != 0){ mdash = m % n. n = ndash. 5. } . Add he ks to the GCD ode to ensure that the numbers typed in by the user are positive.nding problem. 4. For ea h input value you should prompt the user until she gives a positive value.

If you feel this ode will not work. 6. state whether it will not terminate or will terminate but give a wrong answer. 2011. Write a program to . Abhiram Ranade. Do not distribute 111 Note that this is only slightly dierent from the ode whi h we argued must (a) produ e a orre t answer if it terminates. and (b) must terminate.

You do not need to give a formula for your fun tion...". In Se tion 6. Draw a fun tion and an initial guess for whi h Newton's method will os illate between two andidate guesses.g. Hint: use Newton-Raphson and a Taylor series to approximate sin(x).nd ar sin(x) given x.1 we saw a program for . e. 8. \at point A the derivative is . but just draw out the fun tion and des ribe its relevant features. 7.1.

nding the number of digits in a number. just as we did for tk in Se tion 7.1. . you are required to modify the the program from Se tion 6. In that program.1 so that pow is not used.1. In this problem.1. we used the built-in ommand pow. so we might want to not use it. The omputation in pow is somewhat involved. Hint: Compute the value of 10d required for this iteration from the value used in the previous iteration.

So how then. you realize that it was a fairly \stupid" mistake. we make a few suggestions regarding the general pro ess of program development. should you work towards getting a orre t program? How do you avoid mistakes. big. it often happens that eventually when you dis over why the program did not work. You write a program and then you test it with dierent inputs. Title of book by Andy Grove. For the seemingly simple programs that you have been asked to write so far. Intel Corp. o-founder. perhaps an intuitive pro ess might be . omputers make mistakes so rarely that you an assume that they never make mistakes. small or stupid? In this hapter. Quite likely.Chapter 8 Testing and Debugging Only the paranoid survive. you dis over that it does not work orre tly for some inputs. something that you never thought you would be apable of. And to add insult to injury. Then you perhaps realize your mistake and so you modify your program. for whi h you want to ki k yourself. Writing a program is often a frustrating experien e. Sometimes this pro ess seems to go on for ever { you start thinking: my program is learly orre t. is it possible that the omputer is making a mistake? But of ourse.

ne { ea h programmer does what he/she feels is the right thing to do. there are ertain simple prin iples that ould be followed whi h might help in getting orre t programs faster and without getting frustrated. We suspe t that the temptation to write programs intuitively hoping that they will just work is too strong. But espe ially if you . We present some suggestions for ea h stage of the pro ess: from the time you start thinking about the problem all the way to testing your program. However.

at least then onsider the ideas given below.nd that your intuitive style is making you spend too mu h time orre ting the errors in the programs you have written spontaneously.1 Clarity of spe i. 8.

ation The .

programs dont work be ause the programmer did not learly onsider what needs to happen for some tri ky input instan e.rst step in writing a orre t program is to learly know what you want the program to do. How an you be sure that you ompletely know what the program is expe ted to do. but most often. This might sound obvious. that you have 112 .

Do not distribute 113 onsidered all the possibilities? The best way for doing this is to write down the spe i. Abhiram Ranade. 2011.

ations very learly. By spe i. in pre ise mathemati al terms if possible.

The spe i. ations we mean a hara terization of the output in terms of the input.

ation does not state how the output is to be a tually produ ed. it merely says: if the output satis.

es these onditions then it is to be erti.

It is a good idea to write the spe i.ed as orre t.

and also to use the same variable names in the spe i. ation as a omment in your program.

Let us take an example. What are the spe i. ation as in your program.

But su h intuitive understanding does not onstitute a spe i. whi h we indeed do. ations for the program to ount digits of a number? We think that we understand de imal numbers.

The intuitive understanding must be explained in more pre ise terms. Here is the spe i. ation.

Input: A non negative integer n. Output: Positive integer d su h that d is the smallest integer satisfying 10d > n. ation we used earlier. This is a very good spe i.

i. Further. that 10d >6 n provided d 1 is a positive integer. i.e.e. the onditions are he kable : given a solution d to the problem you an qui kly he k the onditions. he k if 10d > n and whether d is smallest. ation be ause it gives the pre ise onditions that we want the output to satisfy. It is ustomary in writing spe i.

.. Formulating spe i.. ations to state onditions su h as smallest/largest ... satisfying .

Should the ondition be 10d > n or 10d n? You may onsider these questions to be tedious. ations in this manner requires some pra ti e. Also a lot of are is needed. but if you annot answer them orre tly while writing the spe i.

ation. You may be making the same mistake in your program! Writing the spe i. you are unlikely to write the program orre tly.

But in su h ases it is imperative that you write down the spe i. say you want to print the day of a week given the date. ation is tedious if there are many ases.g. e.

just to make sure you understand all the nuan es in the problem. As an exer ise. try writing spe i. ations in omplete detail.

Find the smallest ir le that ontains all the points. This is not a good spe i. pn. It might be tempting to rewrite just what is stated in the problem statement: Input: n points p . Suppose you are given n points in the plane. : : : . pn in the plane. Output: Smallest ir le that ontains all points. p . : : : . ations for the following problem.

ation be ause it does not even give a representation for the output. The spe i.

and what it means for a ir le to \ ontain a point". Here is a better spe i. ation should at least spe ify what we mean when we say \smallest ir le".

This is a good spe i. Output: Point C and a number R su h that the distan e between the point C and ea h point pi is at most R. ation of the output.

it is understood how a point is represented: it is represented as a pair of numbers. Note that this spe i. ation. say the x. y oordinates.

there is no easy way to he k that R is smallest. for all hoi es of C . ation is only partially he kable: given a proposed solution C . 1 1 1 . we an he k whether all points pi are within distan e R from point C . However. R .

Do not distribute 114 8.1.1 Input and output examples Along with writing the spe i. 2011. Abhiram Ranade.

and work out what output you want for those. the input and output are both single numbers. For the digit ounting program. and so this is rather trivial. ations. But even here. you should onstru t sample input instan es. it is a good idea to write down spe i.

numeri al examples. he k whether this agrees with the abstra t spe i. output: 2. So if you write input instan e: 34.

Usually. 2 8. It is possible likewise that we write programs intuitively.2 Program Design In real life. it is important that you be more aware of why you have written a ertain statement and not some other. we a t intuitively more often than rationally. So this brings us to the question of program design. your program will involve some simple ideas that arise from the spe i. ation that you have written. As far as programming is on erned. and so su h he ks are useful. but your program an go wrong be ause of trivial mistakes. Is 2 indeed the smallest number su h that 10 > 34? These may sound like trivial he ks.

ation dire tly. and sometimes some lever ideas whi h may not be obvious just given the spe i.

The simplest program design strategy. is to look at the spe i. perhaps. ation. It is good to be aware of pre isely what ideas you are using at ea h stage.

The spe i. and try to develop a program by brute for e as follows. ation.

Sometimes it is possible to enumerate the possible andidates for the output su h that you will eventually go through every andidate. ation tells us what onditions the output needs to satisfy in terms of the values of the input. In this ase. you simply onsider ea h potential andidate in turn. and he k in your program whether the andidate satis.

es the given onditions. viz. 1.1.1 was of this form: you start at the smallest andidate possible for d. The digit ounting program we saw in Se tion 6. and keep ounting up till you .

In fa t. the enumerative strategy does not work for our overing ir le problem. or it might take too long to enumerate all andidates.nd a d satisfying the ondition 10d > n. R and pi k the pair that satis. this strategy may not always work. That d must be the smallest be ause you already ruled out the smaller hoi es and only then onsidered that value. However. There is just no way to enumerate all possible values of C.

This is the se ond lass of programs you will design in this ourse. This insight required for .es all distan e onditions and su h that R is smallest. So some dierent insight is needed in order to design the algorithm.

try to again use variable names similar to those in the theorem statement. so that the orresponden e is lear. : : : . as the exer ises ask you to show. In lude it as a omment in your program. you an enumerate all possible andidates for the ir le you desire. If your program relies on su h lever theorems.nding the overing ir le is as follows. Theorem 2 The smallest ir le overing points p1 . Noti e that on e you have this theorem. or will have as diameter some 2 points from the set. . After this. And indeed you an use the theorem to write a program. then make sure you have stated the theorem very learly. This way it is easier for you to he k that your program follows what is stated in the theorem. pn will either pass through some 3 non- ollinear points.

115 Abhiram Ranade. 2011. Just as you need to learly understand the spe i. you will be given the appropriate insight. So most of the time. Do not distribute Coming up with insightful theorems like the one above is not quite the subje t of this book. But using the given insight still takes work.

Sometimes the spe i. or the mathemati al theorem in appropriate generality. ation of the problem. you must learly understand the insight. Only then will you be able to use it properly.

but perhaps we will dis uss another problem whi h has a similar stru ture in the text. 1 8. insight will not be presented to you. Often the manual solution is based on some insight/mathemati al theorem. it is useful to have larity about the extended/adapted prin iple that you plan to use.1 On the use of variables We have already mentioned that whenever you de. Finally. Even in this ase. so it is important again to state this insight very pre isely: without that you are likely to make a mistake in using it in your program. So you will have to take the insight dis ussed for that problem and extend/adapt the idea used there for use in your new problem. The key requirement here is to formally state something that you know how to do intuitively. the last approa h to program design.2. whi h is perhaps most ommonly useful in this ourse is: mimi how you would solve the problem manually.

Be lear about whi h variables are omputed in whi h stage. use two variables. you should be able to pre isely state how the program exe utes.ne a new variable. 8.3 Hand exe ute the program A fundamental skill that you must have is to pretend you are the omputer and exe ute the program. Consider breaking up you program into stages. This might require you to do some extra typing when you write the ode. The best way to be sure that you are lear about something is to write it down. Do not be stingy in using the same variable to serve two purposes. learly write down what its purpose is. Espe ially if you . You must do this for small programs and simple inputs. when given some small number. Instead. Add this as omments to your program. as input. give them names whi h des ribe the purpose. Going ba k to the digit ounting program. where in ea h stage you ompute the values of ertain variables. and also what variables ( omputed earlier) on whi h they depend. say 34. but it will make your program mu h easier for yourself to understand.

nd that your program is not working orre tly. 1 C C . Then you might be led to this theorem. hand exe ute it on small inputs. You ould begin by asking: suppose someone laims a given ir le is the answer. What on eivable proof an there be that this is the smallest? This might make you say to yourself: let me try to see if an be shrunk.

I expe t the value of this variable to be 0". I expe t the user to type in a positive value at this stage. it might well be be ause something that you on. making the he k will require some exe ution time. 2011.4 Assertions The import of the previous dis ussion is: you should know how your program exe utes. however. The more you know your program. Do not distribute 116 8. if your program is not running orre tly. Why not a tually he k these expe tations during exe ution? Yes. Or you may say. Your knowledge of the program is often of the form: \at this point in the program. the less it is likely to have bugs. Abhiram Ranade.

you simply pla e the statement assert( ondition). Here ondition must be a boolean expression. and the line number and the name of the program . ondition is evaluated. C++ ontains a fa ility whi h makes it easy to he k your expe tations and produ e error messages if the expe tations are in orre t.dently expe t is not a tually happening. typi ally stating \Assertion failed". Suppose you express a ertain ondition ondition to hold at a ertain point in your program. and if it is false an error message is given. When ontrol rea hes this statement.

h> at the top of your . If the expression ondition is true (as you expe ted it to). To use assert you must in lude the line #in lude <assert.le ontaining the assertion is also given. then nothing happens and the ontrol just moves to the next statement.

if you are debugging your program.le.. Here is another simple use... then you want to be sure that your \ on.. it is on eivable that something might have gone wrong in your dedu tion or that the user is not following instru tion. else if(v == 2) . If the value of the variable v has arisen after a ompli ated al ulation. You an also instead in lude < assert> if you wish. . or after input it from the user. In both ases... Pre and post onditions as will be dis ussed in the next hapter are good andidates for using assertions. You might not write the else statement following the if else thinking that it is not ne essary. But \the statement is not ne essary" is only your expe tation. Suppose you know that a ertain variable v will only take values 1 or 2.. if(v == 1) . The you might originally have written: ..

else assert(false).. else if(v == 2) .. // exe uted only if v is not 1 or 2. ..... So you ould a tually make a he k by writing an assertion.. if(v == 1) .. . before you start suspe ting the rest of the program.dent dedu tion" is a tually orre t. . or that the user is following instru tions.

but it goes up to 2 at 10. But in addition to random input values. What instan es do you hoose? First run it on the instan es for whi h you already hand exe uted the program.7. the number of marks to be given was not spe i. The notion of diÆ ult is of ourse informal. and these might be aught on the simplest input instan es. So you might want to pay more attention to these values: perhaps the program has to be \keenly attentive" and distinguish between 999 and 1000 (even though they are onse utive). So he king the inputs 999. In ase of digit ounting 0 is the smallest value allowed. try some bigger or more omplex input instan es. At 9 the value is 1. For example. everybody is apable of making stupid mistakes. You may wonder how you an feed random numbers to a omputer. For example. but not between 578 and 579 (whi h are also onse utive). So for this you an think of using random input values. you will see that d hanges at powers of 10.5 Testing 117 After you develop the program. For this there are a few strategies to onsider. But here is how you might onsider ertain inputs more interesting. for the overing ir le problem. Another ase of ourse is to he k for the smallest and largest input values allowed. the instan e in whi h all points are randomly pla ed in the plane is perhaps more ommon than the instan e in whi h they are all ollinear. One idea is to generate what you think might be \usual" instan es whi h somehow you think might be \ ommon in pra ti e". 2011. you will test it on some input instan es. We will dis uss this in Se tion 8. say for the digit ounting problem. simple input instan es. Do not distribute 8. you an try to think about whi h input values might be diÆ ult for the program. in the mark averaging program (Chapter 6). If you look at the number of digits d as a fun tion of the input n. You may think this is a waste of time: but remember. After the small. 1000 and so on might be more likely to show up the errors. It is possible that for your problem (say ounting digits) there is no notion of \ ommon in pra ti e". Abhiram Ranade. than say he king 578 or 579. A related ase is programs that take variable size inputs. and whatever the largest value allowed is for representing n on your omputer. The value is 3 at 999 but goes up to 4 at 1000.

we entered 200. Does your program run orre tly if only one mark is given? What if no marks are given i.ed beforehand. an impossible mark value. to indi ate that no more marks would be entered. the .e.

In general your program will ontain if statements. one more suggestion an be given.e. you should try to .rst value typed in is itself 200? These are questions you should have thought about learly when you wrote the program. If so. the exe ution will not follow the same path for every input instan e. Finally. i.

if you are writing a program to print the day of the week given the date. you should surely test using a 29th February in a leap year { quite likely there will be separate ode whi h he ks for this and you want to know that that ode runs orre tly.gure out as many values as possible for whi h dierent statements in your program will need to exe ute { and test the program on those input values. For example. This raises an important issue: you may often want to .

For example.rst he k in your program that a valid input is being given by the user. some user might report that your program does not return onse utive days of the week for the dates 28/2/2011 and 29/2/2011. You may unwittingly believe the user and start hunting for the bug. and is therefore wrong. whi h does not exist! .

Abhiram Ranade.5. Do not distribute 118 8.1 Automated testing: input/output redire tion If you are debugging a program. If the input is long it will take a lot of time and eort to type it in. you an type in all the input that you want to supply into a . 2011. In su h ases. then on ea h run you will have to supply the input.

Say the .le.

le is alled input. the standard input stream. Then when you run your program.txt. you an redire t the in. to take input from this .

will take input from input./a.le rather than from the keyboard. instead of typing . You an reate multiple input .out./a. To do this.out <input. you should instead type % .txt Then the program exe utes and all statements in >> .txt..

les and in su essive exe utions redire t the input from those .

Note that the standard output stream. This way. an also be redire ted. This will redu e your eort and also your frustration. you need not type the input again for ea h run.out >filename then the output will be sent to the ./a. If you write % . out.les.

le filename instead of being shown on the s reen. You an examine the .

le filename at your leisure. you an read or write . This is important espe ially if your output is very long. 8.5.2 File I/O Instead of redire ting standard input or standard output.

For reading .les too.

les you .

rst need to insert the line #in lude <fstream> at the beginning of the .

le. whi h is a stream. along with other lines you may have su h as #in lude On e you have this you an reate a so- alled input stream. The quoted name inside the parentheses tells where the stream will get its values: in this ase. This reates a variable alled myinfile in your program. ifstream myinfile("input.txt"). from whi h you an read values. the statement says that the values will ome from the . by writing: <simple pp>.

txt whi h must be present in the urrent working dire tory. After this.le input. you an treat the name myinfile just as you treat in. whi h will ause a whitespa e delimited value to be read from the . and you an write statements su h as myinfile >> n.

le asso iated with myin.

whi h will reate the variable myoutstream.txt").le into the variable n. and asso iated with the . In a similar manner you an write ofstream myoutstream("output. of type ofstream.

txt. i.e.. You an treat myoutstream just like out. you an write values to it using statements su h as myoutstream << n. The values will get written to the asso iated .le output.

. whi h will get reated in the urrent working dire ory.le.txt. in this ase output.

Do not distribute 119 Here is a program whi h takes the . Abhiram Ranade. 2011.

rst 10 values from a .

txt whi h is expe ted to be present in your urrent dire tory.le squares. and opies them to a .

txt. } int val.txt").5. Noti e that we have hosen to enter an end of line after ea h value. } The values are also printed out on out whi h means they will also appear on the s reen (unless you redire t standard out during exe ution). repeat(10){ infile >> val. ofstream outfile("square opy. whi h will get reated.le square opy.3 End of . while printing to outfile as well as out. outfile << val << endl. 8.txt"). out << val << endl. #in lude <simple pp> #in lude <fstream> main_program{ ifstream infile("squares.

if there is an error while reading. or if the .le and reading errors The variables whi h take the value ifstream as well as the variable in behave in a strange but predi table manner.

above. By an error in reading. say as you did for the statement infile >> val. and the a tual value present in the .le ends. we simply mean something su h as: you have asked for an integer value.

By end of .le or typed in in ase of in was not numeri al.

le we mean that you asked for a value but the .

This would happen in the program given above if. for example. the .le has already ended.

the user an type ontrol-d. and that will be treated by the program as end of the . In the ase where in represents the keyboard. type the letter d while the ontrol key is depressed.txt ontained fewer than 10 values.le squares. i.e.

If either a reading error or an end of .le.

then the on erned stream variable takes the value false. Here is a modi. So in fa t you an he k if either of these onditions happened after ea h reading operation.le o urs.

ation to the previous program whi h makes this he k.txt").txt"). int val. repeat(14){ infile >> val. main_program{ ifstream infile("squares. ofstream outfile("square opy. if(!infile){ .

2011. Do not distribute 120 out << "Reading error or end of file.\n". } } } outfile << val << endl. 8. break. Abhiram Ranade. we note that in C++ the phrase infile >> value auses a value to be read from infile into the variable value. This should not ome as a surprise to you. where the . whi h you should really read as ( in >> a) >> b. this is in fa t the reason you an write statements su h as in >> a >> b.5. and in addition itself is an expression that has a value: the value of the expression is the value of the variable infile.4 Input-Output expressions Finally. out << val << endl.

from whi h another value is read into b. Here is a program that merely opies all values from the . This fa t allows us to write some rather ompa t loops.rst expression auses a value to be read into a. and then the expression evaluates to in.

le squares. pp to the .

while(infile >> val){ // file read in the loop test outfile << val << endl.txt"). and if there is an error or end of . without knowing how many values there were. out << val << endl.le square opy. } The reading happens in the loop test.txt"). pp. } int val. #in lude <simple pp> #in lude <fstream> main_program{ ifstream infile("squares. ofstream outfile("square opy.

and the loop ends.le. Thus the above program will read till there is either an error or the end of the . the reading expression returns false.

5 Assert with .5.le. and ea h value read will be printed on out as well as on outfile. 8.

you should he k that the . after every read operation from any stream.le reading Ideally.

.le did not end unexpe tedly. If the infile is a stream. you might . nor there was any error. then after a statement su h as infile >> val.

nd it onvenient to write assert(infile). .

Do not distribute This will print an error message if an end of . 2011. 121 Abhiram Ranade.

le was dete ted. it will happily ontinue. Note that C++ does not give an error message by itself if there is an error. but merely return junk values on subsequent reads! If you have prepared test . or a reading error happened.

we strongly re ommend that you use assertions after ea h read (putting the read in a loop test is equivalent). and not be ause there is anything ne essarily wrong with the program. What do you do? The most natural response is to try and .les whi h you plan to use as input to test your programs. and yet things go wrong: your program produ es an answer dierent from what you expe t. 8. This way you know that your program is giving the wrong answers be ause you are giving it wrong data.6 Debugging Suppose you follow the above dire tions and are generally very areful.

but that is outside the s ope of this book. If they are not then pla e print statements for an earlier point. If the values are as you expe t at the halfway point. given by say. 1. 3. It is possible to formalize what pseudo-random means. 78. a omputer does not generate truly random numbers. you try to get to a single statement until whi h the values are as you expe t. where a. b. 61. 17. Instead. xi = a xi + b mod M . By examining the values in this manner. you an print out the values of the important variables at some onvenient halfway point. This statement should puzzle you { a omputer is an orderly deterministi ma hine. There is also another onvenient property whi h we will see in a minute. a omputer merely generates su essive numbers of a perfe tly deterministi omputable sequen e whose elements seem to be resemble a sequen e whi h ould have been generated randomly. 18. 2. and he k if the values are as you might expe t. M = 101. 73. b = 43. Perhaps you will agree informally that this sequen e looks random. At this point. 66. and so you put print statements to he k the values at a later point in the exe ution. 0. Fun tions su h as rand whi h return (pseudo) random numbers do use the general idea des ribed above: the next number to be returned is omputed as a arefully hosen fun tion 1 0 . you are usually in a position to determine what is going wrong. How an then a omputer generate random numbers? Indeed. M are suitably hosen integers.7 Random numbers C++ provides you with the fun tion rand whi h takes no arguments whi h returns a random number. For this. Indeed a simple example is the so alled linear ongruential sequen e. 8. 2. Then starting with x = 10. 43. 16.nd out when the program starts behaving dierently from what you expe t. but an be onsidered to be random for pra ti al purposes. or at least more random than the sequen e 0. then learly the omputer is doing something unexpe ted later than the halfway point. 4 and so on. So we will just assume that pseudo-random merely gets the best of both worlds: it is a sequen e that an be generated by a omputer. Say we hoosea = 37. Su h sequen es and their elements are said to be pseudo-random. the next few terms are: 9. but after whi h the values are dierent. indeed we did not say anything about randomness in our dis ussion of omputer hardware (Chapter 2).

what x we hose in the example above. 2011. 122 Abhiram Ranade. Do not distribute of the previous. So the exa t sequen e of numbers that we get on su essive alls to rand depends upon how we started o the sequen e. This .

C++ allows you to .rst number of the sequen e is often alled the seed.

To use rand and srand.x the seed by alling another fun tion srand whi h takes a single integer argument whi h will be used as the seed for the subsequent sequen e. This name is de. A all rand() returns an int in the range 0 to RAND MAX.h> But this is not needed if you are in luding <simple pp>. you would normally need to in lude the line 0 #in lude <stdlib.

e.ned for you when <stdlib.h> is in luded. You an onsider the returned value to be uniformly distributed. i. the value is equally likely to be any integer between the spe i.

The sequen e you get when you .ed limits. an important point about pseudorandom sequen es. Finally.

and returns the following value: u + (v-u)*rand()/(1.0 + RAND_MAX) As you an see this value will be between u and v and uniformly distributed to the extent is uniformly distributed.e. you must all randuv(i. The time ommand returns the urrent time in se onds sin e some midnight of January 1. This will give you uniformly distributed integers between i and j. it would be unlikely that the same sequen e would get generated during the exe ution. In su h ases. Say you modify the program and you wish to he k if it is now orre t. This is a desirable property if you will use it to generate input data. This is for the following reason.x the seed is always the same. Our ommand alls the C++ supplied fun tion rand. you might also want to the program to run dierently on ea h o asion.j.v and returns a random double in the range u through v. You an use srand to set the seed as before. 8.j+1) and onvert it to an integer. 1970.8 Con luding remarks You may .1 randuv ommand in simple pp In simple pp we have provided the ommand randuv whi h takes two double arguments u. rand 8. Suppose your program is not working orre tly for ertain (randomly generated) data. Had the data been truly random. you an expe t it to be dierent on ea h run. or some su h moment.7. i. If you want random numbers between integers i. Clearly. However. you an use the ommand time to set the seed. write srand(time()). sin e you use a pseudo random sequen e. you are guaranteed to get the same sequen e if you set the same seed! Of ourse.

But when it omes to serious programming. if not paranoid.nd all the suggestions in this hapter to be very autious. it is better in the long run to be humble and paranoid. .

while(n>0){ n = n/10. Write the program that . So the program is: main_program{ int n. Then bn=10 has d 1 digits. Abhiram Ranade. Do not distribute 123 8. 2011. d=0. } } out << "There are "<<d<<" digits. Is this program orre t? Would you have written this program if you had followed the pro ess suggested in this hapter? For what values of the input would you test the program? 2. ++d. Here is a \ lever" observation about the digit ounting problem. Suppose a number n has d digits.9 Exer ises 1. Thus we simply ount the number of times we an divide by 10 till we get zero and that will be the number of digits of the number. in >> n.\n".

and show the smallest ir le also on the s reen. What are good test ases for the smallest overing ir le problem? 4. Use Theorem ?? and onsider all possible andidates.nds the smallest ir le overing a given set of points. Later we will see ways by whi h we an rule out some andidates without he king them! 3. Consider the problem of . Allow the user to supply the points by li king on the s reen.

nding the smallest ir le that overs a given set of points. Can you prove the insight presented in the text for solving the problem? .

Chapter 9 Fun tions In the pre eding hapters. we have seen programs to do many things. from drawing polygons and mis ellaneous pi tures to al ulating in ome tax and .

nding the greatest ommon divisor (GCD) and .

e.g. .nding roots. It is on eivable that we will want to write more and more omplex programs in whi h some of these operations.

One possibility is to opy the ode for the operation in as many pla es as is required. This doesnt seem too elegant. Wouldnt it be ni e.nding the GCD. In some languages the terms pro edure or subprogram are also used. 9. In what follows. The term fun tion is used in C++ to denote what we have so far informally alled a ommand. and is also error prone. and how to build su h ommands is the subje t of this hapter. is needed at many pla es. if for ea h frequently used operation you ould somehow onstru t a \ ommand" that ould then be used wherever you want in your program? Just as we have a ommand for omputing the square root.5) an we build a ommand that will ompute the GCD of two numbers when demanded? This an be done. or the trigonometri ratios (Se tion 1.1 De. we will use the term fun tion.

and so would like to have a fun tion whi h omputes this. and return their GCD. As an example. whi h ould then be used. It ould take two numbers as arguments. It is natural to hoose the name g d for this fun tion. suppose you wanted to .ning a fun tion Suppose that we indeed need to frequently ompute the GCD.

we must de.d=47. If we had a g d fun tion as des ribed.d) << endl.nd the GCD of 24 and 36.b=24. } Sin e we dont already have su h a g d fun tion. =99. out << g d(a. main(){ int a=36. then we ould write a very simple main program as follows.b) << endl. out << g d( . and also the GCD of 99 and 47.

ne it. 124 . We dis uss how to do this next.

. } return n. Do not distribute 125 int g d // return-type fun tion-name (int m. while(m % n != 0){ mdash = n.) { // beginning of fun tion body int mdash. 2011. m = mdash. int n) // argument list: (argument-type argument-name . n = ndash.ndash.1: De. ndash = m % n. Abhiram Ranade. } // end of fun tion body Figure 9..

omments indi ate the general form Basi ally. in the de.ning a fun tion to ompute GCD.

In essen e. for omputing the GCD. While the sub-program runs. we must spe ify what needs to happen when the ommand is en ountered during the exe ution of the main program. the idea is to have a small program run. the main program must simply wait. whi h we will refer to as a subprogram must be given the inputs.1 shows the ode for de. (in the present ase. Figure 9. and some me hanism must be established for getting ba k the result (in the present ase the omputed GCD) of the omputation to the main program. the values of the numbers whose GCD is to be omputed). sort of in the ba kground.nition. This program.

The simplest way to use the de.ning g d.

nition is to pla e it in the same .

If you ompile and run that .le as the main program given earlier. before the main program.

as you expe t. In general. then it will indeed print 12 and 1. We an relax this requirement slightly.5. a fun tion de.7. The requirement that the fun tion be pla ed before the main program is similar to the requirement that a variable must be de lared before it is used.le. 47. 36 and 99. as will be seen in Se tion 9. the GCD respe tively of 24.

. argument2-type argument2-name.nition has the form: type-of-return-value fun tion-name (argument1-type argument1-name.. .){ body } The de.

nition begins with type-of-return-value. whi h indi ates the type of the value returned by the fun tion. In the GCD example. the fun tion omputes and evaluates the GCD. so our de. whi h has type int.

nition (Figure 9. Next is fun tion-name.1) mentions this. the name of the fun tion being de.

Any valid identi. we hose to all our fun tion g d. In our example. so that is what the ode states.ned.

together with their types. omes the ode. Next is a parenthesised list of the parameters to the fun tion. m.1.er (Se tion 3. body. It . there are two parameters.3) an be hosen as a fun tion name.n both of type int. that is used to ompute the return value. The body is expe ted to be a sequen e of statements. just as you would expe t in any main program. Finally. In our ase.

whi h we explain shortly.1 Exe ution: all by value Consider our g d fun tion and main program. looping statements. suppose that ontrol arrives at the all g d(a. as if they are variables. However. We des ribe the general rule that determines what happens.4.b). Do not distribute an ontain de larations of variables. Further. there are two additional features. The ode in the body an refer to the parameters. and also mention what happens in our spe i. everything that an be present in a main program.1. 126 Abhiram Ranade. While exe uting the main program. onditional statements. the the body must ontain a return statement. 2011. 9. You might re all that the body of g d ex ept for the last statement is lifted dire tly from Se tion 7.

if it be omes ne essary to resume the alling program. in our ase. the subprogram whi h ontains the all.1) is written down somewhere. Now the body of the alled fun tion is exe uted.2. The g d fun tion has two parameters. The body must refer to variables or parameters stored only in the a tivation frame of the all. m.e. Thus.24. In our ase it simply means fet hing the values of the variables a.2(a) shows the state of the memory at this time. Subsequently.d be ause they are not in the a tivation frame of g d(a. The subprogram will exe ute the ode given in the body of the fun tion. and if spa e needs to be reserved for variables et . .b). and 24 into the area for n.b. 36.b. in this ase. viz. The ode annot refer to variables a. main(). 2. 3. The values of the arguments to the all are opied to the area reserved for the orresponding parameters in the a tivation frame of the all.. We have referred to the memory area used by main() as its a tivation frame. When the .b). it is ontinued exa tly from where it was suspended. The subprogram must be given a separate area of memory so that it an have its own variables. Figure 9. ase.n. 5. The omputer remembers whi h instru tion it was exe uting { by this we simply mean that the address of this instru tion (as dis ussed in Se tion 2. i. is suspended. This is ustomary.n. Immediately. 1. Preparations are made to start running a subprogram. But in general. the ode may refer to the parameters m. it is done only inside the a tivation frame of the all. So spa e will be reserved for storing these two parameters in the a tivation frame. an a tivation frame is reated orresponding to the all g d(a. It is ustomary to refer to this area as the a tivation frame of the fun tion all. Thus in ase of our program. 4. 36 will be opied into the area for m. The arguments to the all are evaluated. Thus in our ase. The exe ution of the alling subprogram. the arguments ould be arbitrary expressions whi h would have to be evaluated. spa e is allo ated in the a tivation frame for storing the formal parameters of the fun tion.

. it auses reation of variables mdash. The spa e for this is allo ated in the a tivation frame of the all. These variables are said to be lo al to the all.ndash. 1 1 We will modify this a bit later.rst statement of the body is exe uted.

The expression following return is alled the return-expression and its value is sent ba k to the alling program. In our ase the exe ution of the fun tion progresses in the usual fashion. In the . 2011. Do not distribute 6. 127 Abhiram Ranade. The body of the fun tion is exe uted until the return statement is en ountered.

9. the return is rea hed. We an . m. n: mn L= G It would of ourse be ni e to write a fun tion for the LCM. the all g d( . only the values of the arguments are sent from the alling program to the alled fun tion. This is easily done using the following relationship between the LCM.b). In this model of exe uting fun tion alls. 8. be ause we marked that memory available for use. After this the next out statement will be exe uted (in whi h we will en ounter the se ond all to g d) and so on. The state of the memory at this point is shown in Figure 9. Does it mean that we need to rewrite the ode for omputing the GCD inside the fun tion to ompute LCM? Not at all. It is worth onsidering what happens on the se ond all to g d. A new a tivation re ord would be reated for this all. The alling program resumes exe ution from where it had suspended. We will see another model later on. The point to be noted is that ea h all requires some additional memory. rather than having to opy the ode. Thus the return value will itself be printed. so that we ould invoke it whenever needed.d) in the ode. 7.24. For this reason.rst iteration of the loop.2 Nested fun tion alls: LCM Suppose now that you wish to develop a program to ompute the least ommon multiple (LCM) of two numbers. Thus 12 is opied for our example. The test at the beginning of the iteration fails and the loop terminates be ause 24 mod 12 is indeed 0.n have values 36. So the next statement after the loop. L. but that would require us to ompute the GCD itself. this model is often termed as all by value. The a tivation frame of the all is not needed any longer. and the GCD.e. G of two numbers m. i. We ould use the above relationship. whi h is required to be printed. The same set of a tions would repeat.12.2(b). and very likely it would use the same memory as was used for the a tivation re ord of the previous all. At the end of this iteration. 9. and that area is marked available for general use. but only for the duration of the exe ution of the all. In our ase the all was g d(a. The return-expression is n whi h has value 12. the values have be ome 24. The value of the return expression is opied from the a tivation frame of the all to a spe ial lo ation in alling program. The returned value is used in pla e of the all itself.

b) a : 36 m : 36 b : 24 n : 24 : 99 d : 47 (a) After opying arguments. 2011.b) a : 36 m : 24 b : 24 n : 12 : 99 mdash : 24 d : 47 ndash : 12 (a) At the end of the . A tivation frame of main() A tivation frame of g d(a. Do not distribute 128 A tivation frame of main() A tivation frame of g d(a. Abhiram Ranade.

2: Some snapshots from the exe ution of g d(a.b) simply all the g d fun tion.rst iteration of the loop in g d. Figure 9. sin e we have already written it! So here is how we an de.

When this expression is en ountered. one for main(). whi h involves reating the a tivation frame for this all.24). we will en ounter the expression g d(m. int l m(int m.ne the a fun tion to ompute the LCM.24. Suppose in main we need to al ulate the LCM of 36 and 24. we will need to run a subprogram for l m.24). we will need to start a subprogram for g d. To pro ess this all.24) and another for g d(36. } The exe ution of l m follows the same idea as in our dis ussion earlier for g d.n). As this subprogram exe utes. So it ontains the expression l m(36. This is perfe tly . So at this point.n) with m. one for l m(36. int n){ return m*n/g d(m. we will have 3 a tivation frames in memory.n taking the values 36.

ne! When the subprogram for g d(36.24) .

n) an now be evaluated to be 36*24/12=72. 12.n). Rather than doing the work required to . the omputation of main() will resume with the re eived value.24) returns ba k to main().3 The ontra t view of fun tion exe ution While it is important to know how a fun tion all exe utes. the agent en ounters a statement su h as l m(36. a dierent. metaphori al view is useful. The result 12. We think of the main program as an agent doing its work as des ribed in its program. This will in fa t be the value that the subprogram l m(36. then the result. The idea is to think of a fun tion all as giving out a ontra t to get a job done.nishes. Suddenly. will be used in pla e of the all g d(m.24). will be sent ba k to the subprogram for l m(36. Thus the expression m*n/g d(m. while thinking about fun tions.24). At this point. 9.

This agent is the subprogram for the all l m(36. that stit hing the ollar of a shirt is a spe ialized job. This is not unlike engaging a tailor. 9. and waits for the result to be sent ba k. It so happens.24). whi h most tailors would in fa t ontra t out to ollar-spe ialists. Do not distribute 129 ompute l m(36.24) whi h in turn is waiting for g d(36. giving the tailor the loth and measurements. The main program agent sends the input data to the subprogram agent. 2011.1 Fun tion spe i.3. Abhiram Ranade. Thus it is possible that we may be waiting for the tailor to send us ba k the shirt. the main program agent engages another agent. and the tailor might be waiting for the ollar spe ialist to send ba k a ollar. Noti e that this is very similar to main() waiting for l m(36. The similarity extends further.24) itself. and waiting for the tailor to send ba k a shirt.24). There is nothing to prevent the tailor from further ontra ting out the work to others.

We dont worry about how the tailor does it. we would probably go mad! Likewise. or sub ontra t it out further to one or more raftsmen { that is not our on ern. like a ontra t and is ustomarily alled the spe i. The tailor may do all the work. and what our a ountant should be doing. but we merely hold the tailor to deliver us a good shirt (and at the right time and pri e. when we all a fun tion in our program. as per what has been agreed). If we tried to worry about what our tailor should be doing. ation A key point to be noted from the tailor example above is that when we ask for a shirt to be stit hed. and what our do tor should be doing. we do not think of how exa tly it will get exe uted. we generally do not worry about what the tailor will do. We merely fo us on the promise that the tailor has made to us { that a shirt will be delivered to us. We merely ask: what exa tly is being promised in the exe ution of this fun tion? The promise. is a tually both ways. and so on.

ation. The spe i.

ation of g d ould be as follows: A all g d(m.n) returns the greatest ommon divisor of m.n. You will noti e that the spe i. where m.n must be positive integers.

nothing prevents a alling program from supplying negative values or 0. Responsibilities of the alling program: To supply values of m. The spe i. and the alled program. However. Noti e that C++ already prevents you from supplying fra tional values when you de lare the type of m. ation lays down the responsibilities of both the alling program.n su h that they are positive integers.n to be int. 1.

as will be dis ussed in Se tion 9. ation says that the programmer who wrote the fun tion g d makes no guarantees if you supply 0 or negative values.4. The onditions that the input values are required to satisfy are often alled the pre- onditions of the fun tion. Responsibilities of the alled program: If the alling program full. the alling program might also have to deal with post- onditions. In addition. 2.

and only if the alling program full.lls its responsibilities.

lls its responsibilities. does the alled program promise to return the greatest ommon divisor (or do whatever was expe ted of it). No guarantees are given if the pre onditions are not satis.

. or terminate with an error. or the program may never terminate. Thus in ase of g d. if a negative value or zero is supplied: nonsense values will be returned.ed.

2011. Do not distribute 130 It is extremely important to learly write down the spe i. Abhiram Ranade.

thinking that the spe i. ation of a fun tion. You may sometimes avoid doing so.

ation is obvious. a more general de. But it may not be so! For example.

nition of GCD might allow one of the numbers to be zero. in whi h ase the other number is de.

If this is the de.ned to be the GCD.

he/she might supply 0 as the value of the se ond parameter n.nition a user is familiar with. This will ertainly ause the program to terminate be ause of a division by zero in the very .

rst step of our ode. To prevent su h misunderstandings. it is best to write down the spe i.

ations in full detail. The natural pla e to write down the spe i.

ation is immediately before the fun tion de.

nition.n > 0 { . } Please get into the habit of writing spe i. int g d(int m.n // PRE-CONDITION: m.. So your fun tion for g d should really look like the following.. int n) // Fun tion for omputing the greatest ommon divisor of integers m.

Note that in the spe i. ations for all the fun tions that you write.

often referred to as the des ription of the implementation of the fun tion is also important. But this should be kept separate from the spe i. and for what pre onditions. A des ription of how the fun tion does what it does. but only what the fun tion does. ation it is important to not write how the fun tion does what it does.

n) = GCD(n. For example. The ommand forward is prede. forward. but itself does not stand for any value. then GCD(m. then GCD(m. You have already seen su h fun tions. e. // If n does not divide m. The des ription of how an be in a separate do ument. or ould be written as omments in the body of the ode of the fun tion.n) = n. the following omment might be useful to explain how the g d fun tion works.g. m mod n) This omment ould be pla ed at the beginning of the loop. 9.4 Fun tions that do not return values Every fun tion (or ommand) does not need to return a value. // note the theorem: if n divides m. whi h auses the turtle to move forward. ation.

ned for you. but you an also de.

Suppose we name it polygon. it must take two arguments. an integer giving the number sides. you might wish to build a fun tion whi h draws a polygon with a given number of sides. and a float giving the side length.ne new fun tions or ommands that do something and do but do not return a value. and having a ertain given sidelength. Clearly. For example. The fun tion does not return any value. so we are required to spe ify the return type in the de.

sin e nothing is being returned. . Also. float sidelength) // draws polygon with spe ified sides and spe ified sidelength. void polygon(int nsides. we merely write return with no value following it.nition to be void.

Similarly. right(360.0/nsides). A post- ondition is also a part of the spe i. } return. Abhiram Ranade. Do not distribute // // // // // { } 131 PRE-CONDITION: The pen must be down. Note the pre ondition: it states where the polygon is drawn in omparison to where the turtle is pointing. The pen is down for(int i=0. and the turtle must be positioned at a vertex of the polygon. POST-CONDITION: At the end the turtle is in the same position and orientation as at the start. pointing in the lo kwise dire tion along an edge. is said to be a post- ondition of the fun tion. i<nsides. we should mention where the turtle is at the end. this will be needed in order to know how to draw subsequently. 2011. A ondition su h as this one. whi h will be true after the exe ution of the fun tion. i++){ forward(sidelength).

we might want to write \IIT MUMBAI". without the horizontal lines at the top and bottom. we will have a fun tion drawI for drawing the letter 'I'.5 A text drawing program We would like to develop a program using whi h it is possible to write on the s reen using our turtle. How should we organize su h a program? A natural (but not ne essarily the best. For example. see the exer ises) way of organizing this program is to have a separate fun tion for writing ea h letter. Suppose we de ide that we will write in a simple manner. ation. so that the letter 'I' is just a line. For example. What is the spe i. 9.

But where should the line get drawn? This must be mentioned in the spe i. ation of drawI? Clearly it must draw the line as needed.

It is ustomary to all this re tangle the bounding-box of the letter. and point towards the dire tion in whi h the writing is to be done. in the dire tion the turtle is pointing. but a sequen e of letters. Where would we like the turtle to be at the end of writing one hara ter so that the next hara ter an be written easily? Clearly. ations. the most onvenient . Then we will make it a onvention that the turtle must be brought to the bottom left orner of the bounding box. It is tempting to say that the line will get drawn at the urrent position of the turtle. So it is important to bring the turtle to a onvenient position for drawing subsequent letters. And what is that onvenient position? Suppose we think of ea h letter as being ontained inside a re tangle. Is this really what we want? Keep in mind that you dont just want to draw one letter.

If the spa e is a part of the bounding box.nal position is pointing away from the right bottom orner. We must also learly state in the pre ondition whether we expe t the pen to be up or down. a natural question arises: is it on both sides of the hara ter or only on one side (whi h?)? We should not only answer these questions. pointing in the dire tion of writing. but must also in lude the answers in the spe i. Also whether the inter- hara ter spa e is a part of the bounding box or not.

. ation.

Abhiram Ranade. 2011. Do not distribute 132 Based on the above onsiderations. drawI ould be de.

fa ing in the dire tion of writing. the exe ution refers only to its a tivation frame.sp). float sp){ /*Draws the letter I of height ht. Fun tions for other letters are left as exer ise for you. left(90). and hen e the variables in the main program are not visible.ned as follows.sp). drawA(ht.sp). When the main program is exe uting. return. as well as the fun tions have parameters alled ht and sp. the a tivation frame of the fun tions is not even present. drawI(ht. drawU(ht.sp). our main program ould be as follows. Pen must be up. You will see that there are lo al variables named ht and sp in the main program. forward(ht).sp). void drawI(float ht. forward(sp/2). sp=10. */ } forward(sp/2). drawM(ht. left(90). drawB(ht. forward(ht). turtleSim(). left(90). forward(sp). left(180). When the fun tion is being exe uted. POSTCONDITION: The turtle is at the bottom right orner of the bounding-box. This is a eptable. // turtle is pointing East at the beginning. so there is no onfusion possible. } A remark is in order.sp). penDown().sp). . So assume that you have written them. main(){ int ht=100. fa ing the writing dire tion.sp).sp). drawM(ht. PRECONDITION: the turtle must be at the left bottom of the bounding-box in whi h the hara ter is to be drawn. Bounding box in ludes spa e. drawT(ht. drawI(ht. with pen up. Then to write our message. penUp(). drawI(ht. leaving sp/2 units of spa e on both sides. loseTurtleSim().

6 The main program is a fun tion! The main program that we have been writing. Abhiram Ranade. 2011. Do not distribute 133 9. main program is in fa t a fun tion that we have been de.

so what you spe ify as the main program is in fa t the body of a fun tion alled main whi h takes no arguments. The simple pp hanges the phrase main program that you write into the phrase int main(). The C++ ompiler we have been using.7 Organizing fun tions into . that's why! 9. The main fun tion has return type int be ause of some histori al reasons not worth understanding. ignores this transgression.ning. You may also wondering why we havent been writing a return statement inside main if in fa t it is supposed to return an int. It is a fun tion whi h gets alled by the operating system when you ask for the program to be run. just like all the fun tions we saw in this hapter. the GNU C++ ompiler. and returns an integer.

les It is possible to pla e the main program and the other fun tions in dierent .

If a program is very large.les if we wish. breaking it up into multiple .

and it would be very in onvenient to have all the fun tions in the same . then it is natural to ask ea h programmer to develop dierent fun tions. If a program is being developed ooperatively by several programmers.les makes it easier to manage.

le as they are being developed. A program an be partitioned into a olle tion of .

les provided the following rules are obeyed. Rule 1: If a ertain fun tion f is being alled by the ode in .

le F. textually before the all to f. then the fun tion f must be de lared inside F. Note that a fun tion de.

but not vi e versa.nition is a de laration. We will see what a de laration is shortly. Rule 2: Every fun tion that is alled must be present in some .

9.le in the olle tion.1 Fun tion De laration A fun tion de laration is merely its de.7.

Here for example are the de larations of l m and g d. The names of the parameters an be omitted from de larations. int l m(int m.int). int n). int g d(int m. Suppose a ompiler is pro essing a .nition without the body. you may write just int l m(int. int n).g. e. in the de laration.

and not some typing mistake. and that it may not have been de.36).le ontaining the statement out << l m(24. A de laration of a fun tion f provides (a) an assuran e that f as used later in the program is indeed a fun tion. it needs to be sure that l m is indeed a fun tion. It also needs to know the type of the value returned by l m { depending upon the type the printing will happen dierently. Both these needs are met by the a de laration. When it rea hes this statement..

but it will be de.ned so far.

ned later in this .

le itself or in some other .

Given the de laration. (b) a des ription of the types of the parameters to the fun tion and the type of the value returned by the fun tion.le. the .

le an be ompiled ex ept for the ode for exe uting the fun tion .

Noti e that a fun tion de. Abhiram Ranade. Do not distribute 134 itself.7. whi h an be supplied later (Se tion 9. 2011.2).

nition also provides the information in (a). suppose that we have a main program that alls our fun tion l m to . (b) mentioned above. and hen e is a also onsidered to be a de laration. As an example.

Figure 9. Thus there are 3 fun tions in our program overall: the fun tion main.3 shows how we ould form 3 .nd the LCM of 24 and 36. the fun tion l m and the fun tion g d.

les for the program. First onsider the .

whi h ontains the fun tion g d. It does not all any other fun tion. and so does not need to have any additional de laration.le g d. Next onsider the . pp.

So this .le l m. pp. This ontains the fun tion l m whi h ontains a all to g d.

Finally the .le has a de laration of g d at the very beginning.

le main. so it ontains a de laration of l m at the beginning. pp ontains the main program. Note that the main program uses the identi. This alls the fun tion l m.

whi h says what to do with out.er out to write to the onsole. For this it needs to in lude <simple pp>. The other .

pp g d. so those do not have the line #in lude <simple pp> at the top. There are various ways in whi h we an ompile this program. The simplest possibility is to issue the ommand s++ main. pp l m.les do not ontain anything whi h needs servi es from <simple pp>. pp This will produ e an exe utable .

le whi h will indeed .

7.2 Separate ompilation and obje t modules But there are other ways of ompiling as well.36 when run. 9.nd the LCM of 24. We an separately ompile ea h .

Sin e ea h .le.

an exe utable .le does not ontain the omplete program by itself.

and this an be produ ed by issuing the ommand s++ - filename The option - tells the ompiler to produ e an obje t module and not an exe utable. What the ompiler will produ e is alled an obje t module.le annot be produ ed. Here filename should be the name of a .

pp. In this ase. say main. If dierent programmers are working on dierent .le.o is produ ed. an obje t module of name main.

they an ompile their .les.

and they will at least know if there are ompilation errors.les separately giving the - option. We an form the exe utable .

The linking pro ess will he k that every fun tion that was de lared but not de.o l m.o This use of s++ is said to link the obje t modules together.o g d.le from the obje t modules by issuing the ommand s++ followed by the names of the obje t modules. Thus for our example we ould write: s++ main.

ned in some module is de.

the ode in the dierent modules is stit hed up to form the exe utable . After this he k.ned in some other module.

le. It is a eptable to mix . pp .

o .les and .

e. we ould have issued the ommand .les as arguments to s++.g.

2011. m = mdash. Abhiram Ranade. Do not distribute //----------------------------------------------------------------int g d(int m.){ int mdash. // body ends } //----------------------------------------------------------------- (a) The .ndash. n = ndash. } return n. // body begins while(m % n != 0){ mdash = n. ndash = m % n. int n){ // return-type fun tion-name // (argument-type argument-name..

int n){ return m*n/g d(m. // de laration of fun tion g d. int).le g d. pp //----------------------------------------------------------------int g d(int. } //----------------------------------------------------------------- (b) The . int l m(int m.n).

main(){ out << l m(36.24) << endl.le l m. // de laration of fun tion l m. } //----------------------------------------------------------------- ( ) The . int n). pp //----------------------------------------------------------------#in lude <simple pp> int l m(int m.

3: The . pp Figure 9.le main.

les in the program to .

nd LCM 135 .

pp g d.o l m.o This would ompile main. Do not distribute 136 s++ main. 2011. Abhiram Ranade. pp and then link it with the other .

The result main. 9.o of ompiling will generally not be seen.7.3 Header .les. be ause the ompiler will delete it after it is used for produ ing the exe utable.

Then G has to tell L how to de lare the fun tion g d in the . G. g d. l m.les Suppose programmers M. L respe tively develop the fun tions main.

le l m. pp. The most natural way of onveying this information is to write it down in a so alled header file. A header .

h. A simple strategy is to have a header .le has a suÆx .

le F.h for every program .

le F. pp whi h ontains fun tions used in other .

The .les.

le F. pp that are useful to other .h merely ontains the de larations of all the fun tions in F.

les. Thus we might have .

h ontaining just the line int g d(int. Now the programmer L writing the fun tion l m an read the .int).int).h ontaining the line int l m(int.les g d. and l m.

le g d. it is less errorprone and hen e more ustomary that M will merely pla e the in lusion dire tive #in lude "l m.h" in his . pp. However.h and put that line into l m.

This dire tive auses the ontents of the mentioned .le instead of the de laration.

The mentioned .le.h in this ase) to be pla ed at the position where the in lusion dire tive appears. (l m.

Thus all that is needed in addition is to pla e the .le must be present in the urrent dire tory (or a path ould be given).

pp. as a result of whi h the de laration for l m would get inserted into the . pp.h" in main.h also in the dire tory ontaining main. Likewise M will pla e the line #in lude "l m.le l m.

Note that we ould have used a single header .le main. pp as needed.

le. int g d(int. We ould in lude this single .h ontaining both de larations. say g dl m.int). int l m(int.int).

This will ause both de larations to be inserted into ea h .le in main. pp and l m. pp.

4 Pa kaging software The above dis ussion shows how you ould develop fun tions and supply them to others.7. 9.le. while only one is needed. You reate a F. pp . Having extra de larations is a eptable.

le and the F.h .

le ontaining de larations of the fun tions de.

pp. Next you ompile the F. pp .ned in F.

o .le giving the - option. Then you supply the resulting F.

h .le and the F.

They must pla e the .le to whoever wants to use your fun tions.

le F.h in the dire tory ontaining their sour e .

.e.les (i.

and pla e the line #in lude ``F.h'' in the .les ontaining their C++ programs).

Next.h.les whi h need the fun tions de lared in F. they must also pla e the .

Note that they do not need to see your sour e .o in the same dire tory and mention it while ompiling.le F.

pp if you dont wish to show it to them. .le F.

7. Abhiram Ranade.5 Forward de laration Let us go ba k to the ase in whi h all fun tions are in a single . 2011. Do not distribute 137 9.

We suggested in Se tion 9.1 that a fun tion must be de.le.

the all to it) in the .e.ned before its use (i.

as we dis ussed in the beginning of Se tion 9. However. So if we wish to put the fun tion de. it suÆ es to have a de laration before the use.le.7.

we must additionally pla e a de laration earlier. When writing a program with several fun tions in a single .nition later.

le. many people like to pla e the main program .

We an do this.rst. perhaps be ause it gives a good idea of what the program is all about. it is .

ne to organize the ontents of your .

you should be able to see the entire logi of the fun tion at a glan e: that way it is easier to understand what depends upon what. One way to improve understandability of anything is to present it in small hunks. that most programs an be thought of as working in phases. however. or spot mistakes. You will see later.le in the following order. other orders are also possible. When you write a book it is useful to break it up into hapters. These fun tions ould be pla ed in the same . An example of a thumb rule: every idea that is important should have its own hapter. Of ourse. Basi ally. or its own se tion. in luding main should be longer than one s reenful. How do we break a program into smaller pie es? So far you have not had the o asion to write programs longer than 40 lines. 9. definition of main definitions of other fun tions in any order. fun tions an also be used to make your ode easier to understand to other programmers. de larations of fun tions in any order. There are similar thumbrules for splitting large programs into fun tions. and give it a name that des ribes what it does. a fun tion forms an organizational unit of a program. In a similar manner. Even with large displays. A hapter forms an organizational unit of a book. When it omes to programming. There are a few thumb rules for breaking long text into hapters or se tions. this gives us a limit of perhaps 40-50 lines on the length of a fun tion. it is often believed that no fun tion. This is indeed a very important use of fun tions. Ease of understanding is very important espe ially when programmers work in teams.8 Fun tion size and readability We began this hapter by proposing fun tions as a me hanism for avoiding ode dupli ation. so this dis ussion is perhaps a bit diÆ ult to appre iate. Then you should onsider writing ea h phase as a separate fun tion. However.

le as the main program. but you will .

As noted in Se tion 6.4. Another idea is to make a fun tion out any modestly ompli ated operation you may need to perform. or the value may not stand for itself but in fa t might indi ate that the stream of values has . a user might type in an invalid value. As an example of this.nd that this will make the program easier to understand. onsider the apparently simple a tion of reading in a value from the keyboard.

This idea is partly explored in the read marks into fun tion of Se tion 11.2.nished. One way is to pla e the logi for dealing with all this in a fun tion that is alled by the main program. .

9 Con luding remarks We have remarked about how a fun tion and the main program an have variables with the same name. 3. is dis ussed in Appendix B. and the notion of the s ope of a variable. The general rule for this. Exer ises 1. Write a fun tion that prints the GCD of two numbers. Modify the fun tion polygon so that it returns the perimeter of the polygon drawn (in addition to drawing the polygon). Write a fun tion to . 2011. Abhiram Ranade. 2. Do not distribute 138 9.

be of type bool. Write a fun tion to determine if a number is prime.3 has been written using a single .e.nd the ube root of a number using Newton's method. A ept the number of iterations as an argument. 5. i. It should return true or false. Suppose the LCM omputation program of Figure 9. 4.

and it is noti ed that only the fun tion l m has been de lared and also de.le.

all other fun tions are de.ned.

Show how the program ould appear in the .ned but not de lared.

le. .

A fundamental idea in designing algorithms is problem redu tion. possibly in a manner whi h might surprise you. The strategy of redu ing a problem to another is easily expressed in programs: the fun tion we write for solving the . This is true in our example: quadrati equations are easier to solve than quarti .".Chapter 10 Re ursive Fun tions We are now in a position to des ribe to you what is perhaps the most powerful. what you have learned so far will be used. Of ourse. to solve some diÆ ult omputational problems in a very ompa t manner. What we are going to present will not really ontain any new C++ statements. most widespread problem solving te hnique ever: re ursion. Rather. redu ing one problem into another is useful only if the new problem is in some sense easier than the original. where we might say \Using the substitution y = x + x the quarti (fourth degree) equation (x + x + 5)(x + x + 9) + 7 = 0 redu es to the quadrati (y + 5)(y + 9) + 7 = 0. The notion is very ommon in Mathemati s.

In this ase the redu tion is said to be re ursive. Consider the following rules for dierentiation: d d d ( u + v) = u + v dx dx dx 2 2 2 d d d ( uv ) = v u + u v dx dx dx The . We saw examples of this in the previous hapter. but it is in fa t very ommon.rst problem will all the fun tion for solving the se ond problem. This idea might perhaps appear to be strange. An interesting ase of problem redu tion is when the new problem is of the same type as the original problem.

rst rule. states that the problem of dierentiating the expression u + v is the same as that of . for example.

Noti e that when we redu e one problem to a problem of another type (nonre ursive redu tion). There are two reasons why these rules work: 1. the new problem is required to be of a simpler type. and taking their sum.rst dierentiating u and v separately. 139 . You have probably used these rules without realizing that they are re ursive. For re ursive redu tion. In our example. The redu ed problems are a tually simpler in some pre ise sense. it is enough if the new problem is of a smaller size. be ause u and v are both smaller expressions than u + v . the problem of dierentiating u or of dierentiating v are indeed simpler than the problem of dierentiating u + v.

Abhiram Ranade. 2011. Do not distribute 140 2. Eventually we must have a way to solve some problems dire tly { we annot just keep redu ing problems inde.

Considering dierentiation again.nitely. The problems whi h we expe t to solve dire tly are alled the base ases. suppose we wish to ompute: d (x sin x + x) dx Then using the .

restated for onvenien e. m%n. So in this ase we dire tly write that dxd x = 1.n { if(m % n == 0) return n. We will see an example and a general proof shortly. and we would need to know the base ase sin x = os x. If m%n 6= 0 then GCD(m. n is n. and it turns out that the same me hanism will orre tly ompute the GCD using the above ode.rst rule we would ask to ompute d d x sin x + x dx dx Now. The theorem essentially says that either the GCD of m. n) = GCD(n. But this is exa tly like saying that the derivative of an expression an be written down dire tly or it is the derivative of some simpler expression. n be positive integers. n) = n. as it turns out. To ompute dxd x sin x wed ould use the produ t rule given above. Here is Eu lid's theorem. this is a base ase for the pro edure. the omputation of dxd x is not done by further redu tion. int n) // finds GCD(m. int g d(int m. it would seem tempting. Following the analogy. or it is the GCD of n. Theorem 3 (Eu lid) Let m.1 Eu lid's algorithm for GCD Eu lid's algorithm for GCD is naturally expressed re ursively. } And the most interesting thing is that it works! In the last hapter we sket hed out the me hanism used to exe ute fun tions. m%n). In this hapter we will see several examples of the idea. else return g d(n.m % n). i. dx Even on a omputer.n) for positive integers m. to all g d from inside of itself. 10. re ursion turns out to be extremely useful. The fun tion g d as de.e. If m%n = 0 then GCD(m.

but they embody an interesting strategy for solving problems.ned above alls itself. Su h fun tions not only work. Su h fun tions are said to be re ursive. .

1 Exe ution of re ursive g d Suppose for the moment that our main program in addition the g d de. Do not distribute 141 Somehow show the values of the variables as well as the position of where to re eive values and perhaps separately how to resume. 2011.1: Exe ution of re ursive g d 10.1. Abhiram Ranade. Maybe even show the ode for ea h with a pointer to the next instru tion? Figure 10.

As we know.} Suppose the main program begins exe ution.n are assigned the value 36.24) << endl.24). Immediately it omes upon the all g d(36.24 respe tively.nition above is: main(){ out << g d(36. Now the exe ution begins in the new a tivation re ord. The . and in this a tivation re ord the parameters m. this auses an a tivation re ord to be onstru ted for the all.

n in this re ord are set to 24. this time for g d(24. So we exe ute the . Now the exe ution of the previous a tivation re ord suspends.12).e. and m. Thus another a tivation re ord is reated. be ause 36 % 24 is 12 and not 0. i. But this ontains the all g d(n.rst he k.m % n). g d(24.12).12 respe tively. Thus we exe ute the else part. m % n == 0 fails. Figure ?? shows the state of the world at this time in the exe ution. and exe ution begins in the new a tivation re ord. Our fun tion all exe ution me hanism must be used again.

12) { now that this value is known. 24 % 12 == 0. Where does this value go? It goes ba k to the pla e from where the urrent re ursive all was made. So we exe ute the statement return n. The se ond a tivation then ontinues its exe ution. This ode was to return the value of g d(24. This goes ba k to the . i. the value 12 is returned there. Sin e the urrent all was made while pro essing the se ond a tivation re ord. there isnt mu h more left to in in this a tivation. However.e. This is indeed true. it is returned ba k.rst statement whi h requires us to he k if m % n == 0. This auses 12 to be returned. So the value 12 is returned also from the se ond a tivation. 12.

The .rst a tivation.

2 Interpretation of re ursive programs In some ways there is nothing more to be said about re ursive programs { the last se tion said it all. You might also have observed that the values assigned to m.rst a tivation resumes from where it was suspended. then it is possible that the agent might further sub- ontra t it out to another (sub-)agent.4. When this happens. So as you an see. while you wait (are suspended).1. the orre t value was omputed and printed. 12.n in su essive a tivation re ords in this program were in fa t the same values that m. it prints out the re eived value. If the work taken up by the agent is too ompli ated.n re eived at su essive iterations our original non-re ursive program in Se tion 7. you are waiting for the agent to . 10. and then main terminates. As per its ode. We mentioned in the previous hapter that a fun tion all should be thought of as ontra ting an agent to do the work you want.

nish. the agent is herself waiting for the sub-agent to .

and possibly the hain might be very long.nish. But so what? .

Suppose further that we de. and yet it seems to be sub ontra ting out work! Suppose you have the task of building a Russian doll. So it makes sense for the fun tion l m to ontra t out the work of g d as was done in the last hapter. but you an open up the doll to see that there is a doll inside. the natural intuition is that you ontra t out work that you annot do yourself. whi h ontains another doll and so on till some fairly small doll is rea hed. But whoever heard of ontra ting out work that you yourself an do? That is in fa t what seems to be happening: the re ursive fun tion g d learly should know how to ompute the GCD. Do not distribute 142 Of ourse. Abhiram Ranade. 2011. whi h is a hildren's toy whi h looks like a doll. whi h annot be further opened up.

This ontinues until a raftsman is asked to build a 0 level doll. 10. First establish that some raftsman an build a level 0 doll without further sub ontra ting. whi h are really a k 1 level doll is sub ontra ted to another raftsman. Imagine that the raftsman builds the outer doll.1.3 Corre tness of re ursive programs The key to proving the orre tness of re ursive programs is to use mathemati al indu tion. the so alled base ase. So this doll is sent ba k to the previous raftsman who adds a doll and makes it a level 1 doll and sends it ba k.ne a k level doll to be a doll whi h ontains k 1 dolls inside. This is the indu tive step. How would you do it re ursively? You would ontra t it to some raftsman. until you eventually re eive the k level doll that you ordered! This is learly a strange way of building dolls { but what you should understand for now is that it an work in prin iple. We see how this works for GCD next. and so on. To prove that the pro ess works orre tly. And so it goes. This is not sub ontra ted but built dire tly. you would use indu tion. you must prove that a raftsman an put together a level i + 1 doll given a level i doll. So let us say that your task is of building a k level doll. whi h is just an ordinary doll. Next. We . Instead the task of building the inner k 1 dolls. but does not work on the inner dolls.

But in the . In our ase. j for all i. The argument is really very similar to that in Se tion 7. The base ase is j = 1. it is natural to hoose the value of the se ond argument as the size of the problem. but we will state it more dire tly this time.rst need to have a notion of the size of the problem being solved.4. The indu tion hypothesis typi ally states that the program orre tly solves problems of a ertain size. j ) orre tly omputes the GCD of i. As an example we will see how to argue that our ode will orre tly ompute the GCD. Our indu tion hypothesis IH (j ) is: g d(i.

and will report 1 as the answer. So let us assume IH (1).rst step of g d(i. Using these we will prove IH (j + 1). IH (j ). In the . j + 1). : : : . So onsider the all g d(i. IH (2). This is learly orre t. 1) we will dis over that i%1 is zero.

whi h is orre tly returned. This is true if j + 1 divides i. But the se ond argument in this is the remainder when something is divided by j + 1. so learly it must be at most j . IH (j ).e. j +1).e. we know that this all will return orre tly. and in that ase j + 1 is the GCD. i. it is the orre t answer. Suppose then that the ondition is false. But by Eu lid's theorem. i%j + 1). we he k whether i%j + 1 equals 0. we know that this is also GCD(i. i.rst step. Thus by one of our assumptions IH (1). return GCD(j. In that ase the algorithm tries to ompute and return g d(j. i%j + 1). . : : : .

So understanding tree stru tures and being able to draw them is useful. in many su h diagrams. to be of a tree. By the way.2 Re ursive pi tures Figure 10.2: An exoti tree Thus orre tness follows by the prin iple of (strong) indu tion. and that may be onne ted to the vi e presidents who report to the president. growing downward. It is ustomary. a tree might depi t the heirar hi al stru ture of many organization. tree diagrams are used in many pla es. using some imagination. and so we will write a re ursive program to draw su h trees. say from the Afri an Savannas. This pi ture has some interesting symmetries. It is ustomary to de. an ea h be seen as a tree.2 shows a pi ture whi h we might onsider. i. our interest in trees goes beyond botany. 10. But also to be noted is the another kind of symmetry: parts of the tree are similar to the whole. the manner in whi h fun tions are alled also have a tree stru ture. 2011. As you will see later. Do not distribute 143 Figure 10. Abhiram Ranade. Thus. the stru ture is re ursive. In fa t we might des ribe a tree as two small trees on top of a \V" shape formed by the bran hes at the bottom.g. the root might represent the president.e. or the portion on top of the right bran h. Clearly. First of ourse there is a symmetry of re e tion about a verti al line through the middle. e. those in turn to the managers who report to the vi e presidents. to draw the tree inverted. however. The portion of the tree on top of the left bran h from the bottom.

Our tree of .ne the height of the tree to be the maximum number of bran hes you travel over as you move up from the root towards the top along any path.

what is the length of the bran hes. and what are the angles at whi h the bran hes emerge.2 has height 5. we need more information. Suppose we de lare that we want both the bran h lengths and the angles between emerging bran hes to both shrink by a . and so do the angles. Do not distribute 144 Figure 10. for example. 2011. on top of ea h of whi h sits a height h 1 tree. Clearly. to draw the pi ture. Of ourse. For the tree shown. the bran h lengths shrink as we go upwards. Abhiram Ranade. we an say that a tree of height h is made up of a root with two bran hes going out.

So we will require that at the beginning the turtle to be at the root. and two trees of height h 1 on top.xed shrinkage fa tor as we go up. pointing upwards (pre ondition). and so nothing need be drawn. if we are given the length of the bottom most bran hes. we must arefully write the pre and post onditions for the turtle. we should be able to draw the pi ture. and the height of the tree. As in any drawing program. A tree of height h is just a point. we must draw the root and immediate bran hes. The ode follows the basi observation: to draw a tree of height h. After the drawing is . Now.

On e we . we will ensure that the turtle is again at the root and pointing upwards (post ondition).nished.

void tree(int height. tree(height-1. length*shrinkage. shrinkage). go ba k to root right(angle/2). Clearly. right(angle/2). left(angle/2). float length. the . float shrinkage) // pre ondition: turtle is at root. we draw nothing and return. draw the left bran h left(angle/2). // 1. pointing up. Here is what the program looks like. shrinkage). the program writes itself: we merely have to ensure that we maintain the onditions. } // 3. ensure post ondition left(angle/2). left(angle/2). angle*shrinkage. tree(height-1.x these pre and post onditions. right(angle). // 6. draw right (sub)tree. go ba k to the root // 4. draw the right bran h // 5. forward(length).length*shrinkage. float angle. forward(length). Otherwise. forward(-length). angle*shrinkage. if height is 0. // 2. draw the left (sub)tree. // 7. forward(-length). // post ondition: same { if(height == 0) return.

gure is drawn in a .

145 Abhiram Ranade. numbered in the ode and explained below. 1. Draw the left subtree. For this. the pre ondition ensures that the turtle is pointing upwards. Do not distribute series of 7 steps. so it must turn by half the angle that is meant to be between the bran hes. Draw the left bran h. We . Then we move forward by the length of the bran h. 2. 2011.

120.120. Sin e we know that at the start the turtle is fa ing right. 10. left(90).0. Go ba k to the root. Then we re urse. loseCanvas(). we want to honour the post ondition.1 Hilbert spa e . and then go forward. This is exa tly as we did the left.rst turn so that the turtle is fa ing the top dire tion. its post ondition guarantees that the turtle will fa e dire tly upwards.68). we must supply the arguments. be ause that is a pre ondition for drawing trees. 6. } wait(5). Finally. Ensure the post ondition. we must turn it to the right. After drawing the left subtree. 5. 3. We need to all with height one less. So our main program ould be the following. 7. but also ensure the pre ondition. Go ba k to the root. 4. tree(5. as we did after drawing the left subtree.2. To get ba k to the root we must turn and go ba kwards. and the bran h length and angle shrunk by the given shrinkage value. whi h is a omplished by giving a negative argument to the forward ommand. Draw the right bran h. Sin e the turtle is pointing in the dire tion of the left bran h. so we turn the turtle so that it fa es dire tly upward. main(){ turtlesim(). To all the fun tion. Draw the right subtree. we must turn it left by 90 degrees so that it points upwards.

C and C . The exer ises ask you to understand the re ursive stru ture of the urve. C .e. and are examples of so alled spa e-. an you obtain Ci by omposing some Ci urves with some onne ting lines.3 shows urves C .lling urve Figure 10. These urves were invented by the mathemati ian David Hilbert. This will help to write a re ursive fun tion to draw an arbitrary urve Cn. i. left to right.

lling urves. 1 2 3 4 1 .

Do not distribute Figure 10. 2011.3: Hilbert spa e . 146 Abhiram Ranade.

Other orders are 1.lling urves 10. suppose n = 4. One possibility is to sta k 4 height 1 bri ks.1. Thus if you de.1.1.1.1 or 2. the order of heights onsidered top to bottom is 1.3 Hema handra numbers Suppose you have an unlimited supply of bri ks of heights 1 and 2. or 1. i. You want to onstru t a tower of height n.2.e.1 or 2. In how many ways an you do this? For example.2.2. You an he k by trial and error that no other orders are possible.1.

ne Hn to be the number of ways in whi h a tower of height n an be onstru ted. grammarian who lived in the 11th entury. Hema handra made the following observations. We would like to write a program that omputes Hn given n. The . This problem was solved by Hema handra. we have demonstrated that H = 5. an Indian mathemati ian. poet.

then the problem of building the rest of the tower is simply the problem of building a height n 1 tower. Hema handra observed that if you sele t the bottom-most bri k to be of height 1. but from this it follows: 4 Hn Number of ways of Number of ways of Number of ways of building a tower building a tower = building a tower of = of height n with + of height n with height n bottom-most bri k bottom-most bri k of height 1 of height 2. Thus we have Number of ways of Number of ways of building a tower of height n with = building a tower of = Hn height n 1 bottom-most bri k of size 1 1 .rst observation is that the bottom-most bri k is either of height 1 or height 2. You may think this is rather obvious.

Do not distribute Likewise it also follows that Number of ways of building a tower Number of ways of of height n with = building a tower of = Hn bottom-most bri k height n 2 of height 2 So we have Hn = Hn + Hn What we have written above is an example of a re urren e. an equation whi h re ursively de. 147 Abhiram Ranade. 2011.

in order to solve the problem of size n. H . H = 1. that this single base ase. Now we are ready to write a re ursive program. be ause a height 1 tower an be built in only 1 way { by using a single height 1 bri k. H = 1 is not enough. Clearly.nes a sequen e of numbers. what we need is the base ase. : : : in our ase. The trouble is. So we have a pro edure for redu ing the size of the problem. Is there a problem that we an solve easily? Clearly. We should really ask ourselves: will this allow us to . we need a solution to problems of size n 1 and n 2 respe tively. H .

we an try to .nd H . H and so on? Clearly. we annot even get H with just this information. However.

// H_2 return Hema handra(n-1) + Hema handra(n-2). even for modestly large n. This . So H = 2. you will see that it is very slow.1.1 and 2. as we keep re ursing. learly. // H_1 if(n == 2) return 2. // H_{n-1} + H_{n-2} } If you run this. there are only 2 ways: 1. so eventually the we will want the pair 2. But we know the values of H and H .nd H dire tly. The program is then immediate. the pairs of numbers we are asking for redu e by one. 2 1 1 2 2 1 1 2 3 2 2 2 2 1 int Hema handra(int n){ if(n == 1) return 1. But now. The reason for it an be seen in Figure 10. and so the re ursion will indeed terminate.4.

So we have marked the root in the pi ture with the argument. Out of ea h vertex we have one downward going edge for every all made.gure shows the so alled exe ution tree for the all Hema handra(6). In an exe ution tree. 6. Sin e Hema handra(6) requires Hema handra to be alled . the root vertex orresponds to the original all. to the original all.

and then with 4. our fun tion will 4 . But on e we know H using any all to Hema handra(4) subsequent alls are not really ne essary if we an just remember this value. on e as a part of Hema handra(5). you an argue (Exer ise 5) that while omputing Hn. for large n. This goes on till we get to alls Hema handra(2) or Hema handra(1). Sin e these alls do not make further re ursive alls. At the ends of the orresponding bran hes we have put down 5 and 4 respe tively. So the program is quite wasteful. and on e dire tly from Hema handra(6). the all Hema handra(2) happens 5 times. you will see that the all Hema handra(3) happens 3 times.rst with argument 5. the arguments for the orresponding alls. In general. Note that Hema handra(4) is alled twi e. and the all Hema handra(1) happens 8 times. In fa t. there are no outgoing bran hes from the verti es orresponding to these alls. we have 2 outgoing bran hes.

as you might remember. 148 Abhiram Ranade.4: Exe ution tree for Hema handra(6) make at least 2bn= alls to Hema handra. from Se tion 6. To ompute Hn.1. Thus if you want to ompute Hn by using the re ursive algorithm you are expe ting to spend time proportional to at least 2n= . Do not distribute 6 5 4 3 4 3 2 2 2 3 1 2 2 1 1 Figure 10. and indeed omputing something like say H using the all Hema handra(45) takes an enormous amount of time on most omputers. this program will require n 2 iterations. The program given there omputes Hema handra numbers in order. This is a huge number.2.1 Using a loop But there is a better way. 2011.3. 2 2 45 10. Ea h iteration takes a . stopping when the required number is rea hed.

3. it is the same problem as we solved.xed amount of time independent of n. . you will see that H gets omputed essentially instantaneously using the program of Se tion 6. The length of a poeti meter is simply the sum of the lengths of the syllables in the meter. these numbers are more ommonly known as the Fibona i numbers. Indeed. it seems more appropriate to all these numbers Hema handra numbers rather than Fibona i numbers. 45 10. The question he asked was: how many dierent poeti meters an you ompose of a given length? Mathemati ally. Thus we an say that the total time is approximately proportional to n. In fa t it appears that they may have been known in India even before Hema handra. built using syllables of length 1 and length 2. He was onsidering dierent ways of onstru ting poeti meters.2. This sequen e should look familiar to many readers. But Hema handra is known to have studied them before Fibona i. Indeed.1. In any ase.2 Histori al Remarks Hema handra a tually onsidered a dierent problem.

the ith pile ontaining xi stones at the beginning. A move for a player involves the player pi king a pile in whi h there is at least one stone. We will have dierent games for dierent hoi es of xi. 2011. but nevertheless interesting. The game has two players. There are some n piles of stones. say with White moving . say White and Bla k. Do not distribute 10.4 The game of Nim In this we will write a program to play the game of Nim. 149 Abhiram Ranade. and our program will ontain a key idea whi h will be useful in all game playing programs. and removing one or more stones from that pile. This game is quite simple. The players move alternately.

The player that makes the last valid move. Here is a simple example. Then the . is said to be the winner. Or you may say that the player who is unable to make a move on his turn is the loser. after whi h no stones are left.e. i. Suppose White pi ks 4 stones from pile 1.rst. Suppose we have only 2 piles initially with 5 and 3 stones respe tively.

White need not have pi ked 4 stones in the very .rst pile has 1 stone left and the se ond has 3. and then White an pi k only 1 of them. Now Bla k an win by pi king 2 from the se ond pile: this will leave 1 stone in ea h pile. leaving the last one for Bla k. Of ourse.

rst move. Is there a dierent hoi e for whi h he an ensure a win? We will leave it to you to observe that White an in fa t win this game by pi king only 2 stones from the .

rst pile in his .

rst move. determine whether the player whose turn it is to play an win. The notion of a winning position is of ourse intuitively lear to us having played dierent kinds of games from hildhood.e. One way to make this notion formal is to . in luding games su h as hess and even ti k-ta k-toe. that when we say winning/losing position. we mean winning/losing for the player whose turn it is to move. In ase the position is winning. It is ustomary to all the player on move N (next player). no matter what the other player plays. i. So here is the entral question of this se tion: Given the game position. Note by the way. number of stones in ea h pile. we would also like to determine a winning move. and the player not on move P (previous player).

rst de.

Could you then determine if G is winning or losing? Turns out that this an be done easily. and hen e Gi is losing for P . mk in G.ne a notion of a strategy: a strategy is simply a rule whi h tells me what move to make for every position. : : : . The above hara terization gives us a re ursive algorithm for determining if a given position G is winning or losing. But now P is on move. and the positions Gi they lead to. then we get to Gi whi h is losing. Suppose you are told whether ea h Gi is winning or losing. and hen e G must be winning for N ! Thus the only way G an be a losing position is if all Gi are winning. The we determine (re ursively!) whether Gi are winning or losing. no matter how N plays. Then if N hooses mi in G. Now a game position G is said to be a winning position if there exists a strategy S for N su h that if N plays the rest of the game using S he wins no matter how P plays. If we . Suppose now that G is some game position. Suppose some Gi is a losing position. We determine all moves mi possible in G. and N has moves m . Suppose that position Gi results if move mi is made in position G. Similarly G is said to be a losing position (for N as always) if there exists a strategy S 0 for P su h that P wins if he plays the rest of the game using S 0.

nd some Gi that is losing. we de lare G to be winning. We know that in order for a re ursive algorithm to work we must ensure that 2 things: 1 . Otherwise we de lare G to be losing.

++i) // Pi k i stones from pile 1 if (!winning(x-i. This position is learly losing. In our ase this is true in the sense that ea h Gi must have at least one stone less than G. We an argue that eventually we will rea h some (\simplest") problems whi h we an solve dire tly. // if a losing next state is found for(int i=1. // if all next states are winning The fun tion an be alled using a main program su h as the one below. i<=x.y. 2. { if(x==0 && y==0 && z==0) return false. bool winning(int x.z = number of stones in the 3 piles. i<=z. Clearly. In the given position. // returns true if this is a winning position. and false if the position is losing. You an easily modify the program to do this.y. else out << ``Loses. it does not say what move to play if it is a winning position. out << ``Give the number of stones in the 3 piles: ``. we an hoose to take stones from either the .''<<endl.z)) return true. The fun tion winning given below takes a game position and returns true if the position is winning. } Our fun tion only says whether the given position is winning or losing.z-i)) return true. Do not distribute 1. 2011. int z) // x. // if a losing next state is found for(int i=1.y. 150 Abhiram Ranade. ++i) // Pi k i stones from pile 3 if (!winning(x. if (winning(x. we must rea h the position in whi h all piles have zero stones.z)) return true. in >> x >> y >> z.'' << endl. ++i) // Pi k i stones from pile 2 if (!winning(x. // base ase for(int i=1. Ea h subproblem we are required to solve is simpler than the original.y. int main(){ int x.y-i. int y. and is hen e simpler. The logi of our fun tion should be lear.y. we know this dire tly. // if a losing next state is found } return false.z)) out << ``Wins. as you are asked in the exer ises. but you an see that it an be easily extended for a larger number of piles. We give this program for the ase of 3 piles. Thus we an write a program to determine whether a Nim position is winning or losing.z. i<=y. as we keep removing stones.

rst pile. or the third pile. The . the se ond pile.

rst loop in the fun tion onsiders in turn the ase in whi h we remove i stones from the .

This .rst pile.

Abhiram Ranade.y. i. The subsequent loops onsider the ases in whi h we remove stones from the se ond and third piles.z stones respe tively. We re ursively he k if this is a losing position. must be a winning position. the original position. Thus we return true immediately. If so. 2011. Do not distribute 151 leaves the new position in whi h the number of stones is x-i. as per the dis ussion above. in whi h there are x. If we .e.y.z.

and so we return false in the last statement of the fun tion.1 Remarks It turns out that there is a more dire t way to say whether a given position is winning or losing. then indeed the original position must be losing.4. We will not over this.nd no losing position after he king all moves. and performing additions of the bits modulo 2 and so on. This is very lever. 10. but you should be able to . involving writing the number of stones in the piles in binary.

2. and the unknowns x. The most important idea in this hapter on erns algorithm design: if you want to solve an instan e of a ertain problem. Hema handra probably also dis overed the solution to his problem thinking in this manner. n) = GCD(m n. writing the program re ursively is not always the best way. However. re ursion is an important tool in writing game playing programs. Write a re ursive algorithm based on this idea. Devise a method to . It is likely that Eu lid dis overed his GCD algorithm possibly thinking in this manner. Note that Eu lid's theorem merely applies the idea of subtra ting n as many times as possible. It is quite likely that Hema handra also solved his problem by thinking re ursively. Exer ises 1. Suppose that m > n > 0 are positive integers. be ause the general stru ture of the program applies for many 2 player games.nd it dis ussed on the web. Show that GCD(m. The notion of re urren es is also important. Indeed. 10. b. Tree stru tures are important in omputer s ien e. Consider an equation ax + by = . where a.5 Con luding remarks A number of points need to be noted. and ask: will the solution of smaller instan es help me in solving the larger instan e. But we must remember that sometimes it may not be best to write the program re ursively. are integers. It is often a good idea to think re ursively for the purpose of solving problems. y are required to be integers. Su h equations are alled Diaphontine equations. n). You will see more uses of trees later in the book. Then it helps to assume that you an solve smaller instan es somehow. Our program is nevertheless interesting.

nd a solution to Diaphontine equations. Hint1: redu e the problem to .

b. Show that in this ase an integer solution is easily obtained. 152 Abhiram Ranade. b0 is in some sense smaller than a. b by doing a variable substitution. 5. Hint2: Suppose a = 1. 2011. Write a program whi h takes a. 4. as input and gives a solution. Do not distribute 3. Dedu e the general stru ture of Hilbert spa e . solving a0x0 + b0y0 = where a0 .

Write a program to draw a Hilbert spa e .3.lling urves by observing Figure 10.

hen e Bn gives a good estimate of the number of operations needed to ompute Hn .4. Hn . (a) Write a re urren e for Bn and use it to write a program that omputes Bn. onsidering Figure 10. What are the base ases for this? Make sure your answer mat hes the bran hes in the trees of Figure 10. Write a program that prints the table Hi versus i. Note that ea h bran h ends in a all to Hema handra. What is it? The depth of the re ursion is de. (b) Argue using indu tion that Bn 2bn= for n 3. Prove using indu tion that 2bn= Hn 2n. There is something interesting about the arguments to the su essive re ursive alls. Based on this what data type would you use for omputing H ? If it helps you may note the stonger result Hn 1:62n 2n= : .lling urve Hn given n.4. Suppose you all the fun tion g d on onse utive Hema handra numbers Hn. Thus B = 14. Let Bn denote the number of bran hes in the re ursion tree for Hn.

be ause all bran hes go to the same height. draw Hem(6) should be able to onstru t the tree shown in Figure 10. (botani al) trees have a single trunk that rises verti ally. the time to ompute the g d will be at most proprortional to the number of bits in the numbers. argue that the time taken by g d when alled on n bit numbers ould be as large as n=2. Hn)? Based on this. 11. n and so on.ned to be the number of onse utive re ursive alls made. You ould onsider variations su h as: bran hes grow out of the trunk. 6 2 6. Suppose the initial all is with arguments m . 0 3 9.4. or at the top. Write a fun tion draw Hem that draws the re ursion tree for alls to Hema handra. Binary. In other words. Consider the g d fun tion developed in the hapter. Complete. n . say you only have one bran h on one side and the entire tree on the other. So you ould onsider a tree to be \one verti al bran h. 10. whi h may ontinue further. n . Express these tree growth patterns re ursively as well. Does this apply for the g d fun tion that you are asked to write in Exer ise 1? More ommonly. 2 1 43 80 7. then m . and then splits into bran hes. The tree drawn in Figure 10. then m . Based on this argue that a all to g d with n bit numbers will have depth of re ursion at most 2n. What is the depth of the re ursion for the all g d(Hn . Show that ni ni . You ould have an in omplete binary tree also. Draw trees expressing this idea as a re ursive program. i. +1 +1 8. where they are no bran hes. be ause at ea h bran hing point there are exa tly 2 bran hes. with two trees growing out of it at an angle".2 is alled a omplete binary tree. n and su essive alls are made with arguments m . 3 0 1 +2 1 2 2 .e. ea h nested inside the pre eding one.

and in the ode your merely repla e the ith letter by i. and so on till 'z' by 26. 14. Write a fun tion whi h returns a 0 if the given position is losing. say 1 digit per line (so 2120 will be given on 4 lines). Make sure you ask as few questions as possible. Further. some strings will have more than one interpretation. Say your message only onsists of the letters 'a' through 'z'. there are no separators between the numbers orresponding to ea h letter. Thus 'a' will be oded as 1. but if the position is winning. Abhiram Ranade. and the more signi. Write a fun tion that says whether a position is winning for this game. How will you determine whether a position is winning or losing for this new game? In another variation. Suppose you are given a string of numbers. Devi e a system of questions using whi h you an determine how to move the turtle. z the number of stones in the piles for the given position. You are to write a program that takes su h a sequen e of numbers and prints out the number of ways in whi h it an be interpreted. Clearly. the last m digits will give the number of stones to pi k. where 10m is a power of 10 larger than x. the word \bat" will be oded as the string 2120. 16. You are free to demand that the input be given from the last digit if you wish. 13. Suppose you want to send a message using the following very simple ode. 153 Write a program whi h takes inputs from the user and draws any binary tree. Thus. i. you are allowed to pi k either any non-zero number of stones from a single pile. With this en oding. One variation is: the player who moves last loses. y. Suppose to any request the user will only answer 0 (false) or (true). 'b' as 2. There are many variations possible on the game of Nim as des ribed above. returns a value that somehow indi ates what move to make. to indi ate that s stones should be pi ked from pile p. For example. De ide on a suitable en oding to do this. the string 2120 ould also have ome from \ut".e. 15. or an equal number of stones from two piles. 2011. Do not distribute 12. return the number p 10m + s.

Some of you might wonder whether we an return pairs of numbers out of a fun tion (without having to en ode them as above) { we will see how to do it later in the book. Write a re ursive fun tion for . ant digits will indi ate the pile number.

nding xn where n is an integer. Try to get an algorithm whi h requires far fewer than the n 1 multipli ations needed in the natural algorithm of multiplying x with itself. . Then build up on this. Hint: Show that k multipli ations suÆ e if n = 2k is a power of 2.

and see how this an also over ome the said diÆ ulties.Chapter 11 More on Fun tions In this hapter we dis uss a mis ellaneous set of advan ed features related to fun tions. We study this next. The way to over ome these diÆ ulties is to use the me hanism of all by referen e for passing parameters. We then dis uss the notion of fun tion pointers.1 by stating some relatively simple things we would like fun tions to do. We also study the losely related notion of pointers. We then study how default values an be spe i. using whi h we an ee tively pass one fun tion as argument to another fun tion. We begin in Se tion 11. but whi h annot be done using what we have learnt so far.

ed for some of the parameters to a fun tion. we onsider the notion of fun tion overloading.e. Finally. how the same fun tion name an be used to de. i.

we might want to write a fun tion whi h takes as arguments the Cartesian oordinates of a point and returns the Polar oordinates.1 Some diÆ ulties There are a few seemingly simple things we annot do using our urrent notion of a fun tion. not two. This is not immediately possible be ause a fun tion an only return one value. 11. Another example is: suppose we want to write a fun tion alled swap whi h ex hanges the values of two integer variables. For example. Suppose we de.ne more than one fun tions.

a = b.q in the main program. int b){ int temp.ne something like the following.b. b = temp. 154 . void swap(int a. it does ex hange the values a. temp = a. and their ex hange does not have any ee t on the values of p. } // will it work? If we all this by writing swap(p. but a.q whi h are in the a tivation frame of the main program.b are in the a tivation frame of swap. The reason for this is that when swap exe utes.q) from the main program. we will see it does not hange the values of p.

It will read the next mark into the variable given as the argument. But what we have learned so far does not allow us to write this fun tion: The value of the argument nextmark will be opied to the parameter of the fun tion. you want the hange to be re e ted in the orresponding argument? Just say so and it is done! The way to \say so" is to de lare the parameter whose value you want to be re e ted as a referen e parameter. i. true if the value read was not 200. So in ase you are. Do not distribute As a third example. First of all. Our hope is that we an write a fun tion read marks into that will behave in the following manner. There are a number of reasons for dis ussing the C solution. while(read_marks_into(nextmark)){ sum = sum + nextmark. alled all by referen e. then the loop needs to terminate. the C solution uses the notion of pointers. float &theta){ r = sqrt(x*x + y*y). int ount=0.e. the C solution might help you understand \what goes on behind the s enes" in all by referen e. int main(){ float nextmark. be ause essentially all C programs are also C++ programs. theta = atan2(y. Here is an attra tive way to write the program. Following that we will see how the problem is solved in the C language. 155 Abhiram Ranade.x). Se ond. 11. float y. whi h are needed in C++ also. by adding an & in front of the name of the parameter. ount = ount + 1. you may see our so alled C solution in C++ programs written by someone. onsider the mark averaging program from Chapter 6. It turns out that all the 3 problems listed above have a ni e solution in C++. . void Cartesian_To_Polar(float x. So here is how we might write the fun tion to onvert from Cartesian to Polar. float &r. Finally. sum=0. and also return a true or false depending upon whether the reading was su essful. but will not be opied ba k. 2011. Also. and false if it was. We will see this next. } } // will this work? out << ``The average is: `` << sum/ ount << endl. This solution is based on another way of passing arguments to fun tion. it is good to know the C solution be ause C is still in use.2 Call by referen e The idea of all by referen e is simple: when you make a hange to a fun tion parameter during exe ution. C++ is onsidered to be an enhan ed version of C. An important step in this program is to read the marks from the keyboard and he k if the marks equal 200. the C solution is in fa t a less magi al version of the all by referen e solution of C++. substantially. If the marks equal 200. As you might know.

This an be alled in the normal way...theta1) exe utes. out << x << " " << y << endl.r1. and so nothing is opied into the a tivation area of swap2. possibly as follows. The values of x1. so at the end \6 5" will be printed. the variable r1 would ontain p1 + 1 = 2 1:4142.theta1 instead! Thus. Hen e whatever hanges the fun tion seems to make to a referen e parameter are really made to the orresponding argument dire tly. So indeed. x = y. The parameters a. The fun tion to swap variable values an also be written in a similar manner.theta1). Our last example is also easy to write. and these would be printed out. the assignments in the statements r=. swap2(x. } Both the arguments of swap2 are referen es. as mentioned. out << r1 << `` `` << theta1 << endl. . Abhiram Ranade. r1. as CartesianToPolar exe utes. y=6. ee tively we exe ute temp = x. No storage is allo ated for a referen e parameter in the a tivation frame of the fun tion.. and theta1 would ontain tan 1 = =4 0:785.0. a referen e parameter dire tly refers to the orresponding argument. theta1.y1 are opied to the orresponding parameters x. all referen es to r. int main{ int x=5. Do not distribute 156 } In this fun tion. and theta=.b refer dire tly to x.y.y).0. b = temp. temp = a. when the fun tion returns. b = temp. y1=1..y. } Here is how the all CartesianToPolar(x1.e. However. Instead. Cartesian_To_Polar(x1.y1. a = b.y1. the values of r1. This will learly ex hange the values of x.y. 1 void swap2(int &a. } This an be alled as follows. theta in the fun tion are deemed to be referen es to the variables r1. 2011. get made to r1 and theta1 p dire tly. int &b){ int temp. theta1 are not opied. r and theta have been de lared to be referen e parameters. during the exe ution of the fun tion. int main(){ float x1=1. i.r1. nor is the value of the orresponding argument opied. Instead.

the . } This fun tion will work with the main program as given earlier. 2011. Do not distribute 157 bool read_marks_into(int &var){ in >> var. When the fun tion exe utes. return var != 200. Abhiram Ranade.

So the while loop in the main program will indeed terminate as soon as 200 is read.3. and yet the loop termination is by he king a ondition at the top. The expression var != 200 is true if var is not 200. When we see a fun tion all. This makes it hard to read and understand ode. Continuing the dis ussion at the end of Se tion 6. no matter whether we use all by value or by referen e for a parameter.rst line will read a value into var.1 Remarks Call by referen e is very onvenient. we note that perhaps this is the ni est way of writing the mark averaging program: we do not dupli ate any ode. rather than using a break statement in the body. 11. we need to either . However two points should be noted.2. But var is a referen e for the orresponding parameter nextmark. and false if it is 200. The manner by whi h we spe ify arguments of a fun tion in a all is the same. and hen e the value will in fa t be read into nextmark.

nd the fun tion de.

For example. If a ertain parameter in a fun tion is a referen e parameter. we annot write swap2(1. as you will see. So supplying anything other than a variable is an error if the orresponding parameter is a referen e parameter.. would have to mean something like 1 = z.z).2 Referen e variables In the dis ussion above we noted that a referen e parameter should be thought of as just a name. does not have this drawba k.nition or de laration (Se tion 9. dis ussed next. orrespond to referen e parameters.2.7. what it is a name of is .1) to know whi h of the arguments. then the orresponding argument must be a variable. if any. do see Se tion 14. and hen e might hange when the fun tion returns. whi h is meaningless. 11. This would make a. The C language solution whi h uses pointers. On the other had it has other drawba ks.z respe tively and then statements in the fun tion su h as a = b.4. However.1.b refer to 1.

int x = 10. The . r = 20. In a similar manner.xed only when we make the all. int &r = x. we an have referen e variables also. out << x << endl. out << r << endl.

rst statement de.

The se ond statement de lares a referen e r. This is spe i. In the de laration itself we are obliged to say what variable r is a name of. hen e the & before the name.nes the variable x and assigns it the value 10.

Thus the se ond statement de lares .ed after =.

3 Pointers We . 10. gets printed in the last statement. 2011. gets printed. this hanged value. we assign 20 to r. In the third statement. we print r. Finally. but sin e r is just a name for x. 20. 11. it really hanges the value of x. the value of that. sin e this is a name for the variable x. Do not distribute 158 the integer referen e r whi h is another name for the variable x.2. Abhiram Ranade. The utility of referen e variables will be ome lear later. in Se tion 21. In the fourth statement.3.

We know from Se tion 2. The address of the .3 that memory is organized as a sequen e of bytes.rst dis uss pointers in general. and the ith byte is supposed to have address i. it gets a set of onse utive bytes.1. When memory is allo ated to a variable. or be at address i. and then say how they are helpful in solving the problems of Se tion 11.

3.rst byte given to the the variable is also onsidered to be the address of the variable.1 \Address of" operator & C++ provides the unary operator & (read it as \address of") whi h an be used to . 11.

this is the same hara ter that we used to mark a parameter as a referen e parameter.2 Pointer variables We an store addresses into variables if we wish. 12. 11. Yes. 14.d. and there is also a binary operator & (Se tion G). Thus some way is needed to denote values 10.e. and for these the letters a. 11. Note that the onvention in C++ is to print out addresses in hexade imal. But for this we need to de. But you will be able to tell all these apart based on the ontext. 13. so you will see something that begins witn 0x. .3. Note that in hexade imal ea h digit takes value between 0 and 15. whi h indi ates that following it is an hexade imal number.nd the address of a variable. This will print out the address of p.f respe tively are used. int p.b. out << &p. 15. Here is a possible use of the unary &.

See below. we may write: int p=15. The . int *r.ne variables of an appropriate type. For example. out << &p << " " << r << endl. // not ``int multiplied by r''! r = &p.

it stores the address of the int type variable p into r. The type int* is used for variables whi h are to be used for storing addresses of int variables.rst statement de lares a variable p as usual. of type int. The next statement should really be read as (int*) r. you will see that the last statement will indeed print identi al hexade imal numbers.e. If you exe ute this ode. i.. int* is the type and r is the name of the de lared variable. This is what the third statement does. .

and you may not write s = &p.s are said to be pointers to p. Note that float* and int* are dierent types. In general. Figure 11. variables of type T* where T is a type are said to be pointer variables. Variables r. Finally. In this we have assumed that p is allo ated bytes 104 through 107. or r = &q. even though we use integers to number memory lo ations. Likewise we may write: float q. 104. 159 Abhiram Ranade. 2011. and r is allo ated bytes 108 through 111.. float* s = &q.1 s hemati ally shows a snapshot of memory showing the ee t of storing the address of p into r. The address of p. appears in bytes 108 through 111. as a result of the exe ution of r = &p. it is never ne essary in C++ programs to expli itly store a spe i.1: Pi ture after exe uting r = &p. Do not distribute Address Content Remarks 104 105 15 Allo ated to p 106 107 108 109 104 Allo ated to r 110 111 Figure 11.. Here we have de lared and initialized s in the same statement.q.

So the ompiler ags it as an error. onstant.3 Dereferen ing operator * If we know the address of a variable. then you an do so by writing w = &v. In fa t. of type int*. into a pointer variable. it is a ompiler error in C++ to write something su h as w=104. *. 11. q. where w is a pointer.3. // both pointers? de lares p to be a pointer to int. but it will be lear from the ontext whi h operator is meant. it is more likely to be a typing mistake.g. Finally it should be noted that C++ de larations are a bit onfusing. If you somehow ome to know that 104 is the address of a ertain variable v. and so you want 104 stored in some pointer variable w. while q is simply an int. the * somehow \asso iates" with p than with int.. if you a tually do. The hara ter * also denotes the multipli ation operator. without using the number 104 itself. and is also used in de laration of pointer variables. . Very simply put. say 104. e. we an get ba k that variable by using the dereferen ing operator. Even if you put no spa e between int and * in the above statement. the unary * an be onsidered to be the inverse of &. The following int* p. Be ause you dont need to write this.

2011. Do not distribute 160 Formally. The unary * is to be read as \ ontent of". For an example. Abhiram Ranade. Then we onsider the memory at address v to be the starting address of a variable of type T.g. onsider the de. e. an expression su h as *xyz above is to be read as \ ontent of xyz". and *xyz denotes this variable. suppose xyz is of type T* and has value v.

r as given above.nitions of p. Then to .

m = *r. int *r. we would really be storing a value into p. But p is exa tly su h a variable. If *r appeared on the right hand side of an assignment. we note that r is of type int* and has value &p. Hen e *r denotes the variable p itself. Thus *r denotes a variable of type int stored at address &p.): *r = 22. or in an expression. Thus. r = & p. we would be using the value of p in pla e of the expression *r.nd what *r means. Thus we may write (after the ode int p=15. int m. if *r were to appear on the left hand side of an assignment statement. In the .

we would store 22 into p. 22 in this ase. In the third statement.rst statement. 11. into m. we would store the value of p.4 Use in fun tions We .3.

void CartesianToPolar(float x. in luding types su h as int* or float*. &r. float y. out << r << `` `` << theta << endl.0. CartesianToPolar(1.theta. int main{ float r. *ptheta = atan2(y.x).0. float* ptheta){ *pr = sqrt(x*x + y*y). 1. } Let us . float* pr. Thus we an write a fun tion to ompute the polar oordinates given Cartesian as follows.rst note that fun tions an take data of any type as arguments. } This ould be alled as follows. &theta).

rst make sure that the types of the arguments in the all and the parameters in the fun tion de.

nition mat h. The .

y are required to be a float. x. and indeed the .rst and se ond parameters.

none of the parameters are referen e parameters. Sin e r is of type float. and so all arguments have to be opied . The third parameter pr is of type float*. Let us see how this will exe ute.0.rst and se ond arguments are both 1. and hen e the type of the third argument and the third parameter mat h. of type float. the type of &r is indeed float*. When the fun tion CartesianToPolar is alled. Similarly the type of the fourth argument &theta is also seen to mat h the type float* of the fourth parameter. The third argument is the expression &r. So learly our program should ompile without errors. whi h means the address of r.

So .rst.

Do not distribute 161 1. 2011. Abhiram Ranade.0 is opied to the parameter x in the a tivation frame of CartesianToPolar. and .0 is opied to y. The se ond argument 1. The third argument &r is opied to pr.

Then the body of the fun tion is exe uted.nally the fourth argument &theta is opied to ptheta. The .

This value is to be pla ed in the variable denoted by the left hand side. So let us onsider the exe ution. temp = *pa. The last statement auses the value in temp. we should use their addresses. even if it appears in the ode of CartesianToPolar will store 2 into the variable r of main.3. the ar tangent will be found to be =4 0:785. Now *pr is interpreted exa tly as des ribed in Se tion 11. int* pb){ int temp. 2 and 0. y=6. } The arguments to the all are &x.785 will be storedpin theta of main. int main{ int x=5. Thus they mat h the types of the parameters of the fun tion. Thus 0. i. the value of y is opied to x.x). the value in x at the beginning to be opied to y (whi h is what *pb denotes). be ause x. It should be lear to you now what we should do: instead of using the variables as arguments. void swap(int* pa. Hen e *pr denotes the variable r of the main program. and *pb in swap will refer to the variable y of the main program. Sin e y. After this the all will terminate. Thus we may note that *pa in swap will really refer to the variable x of the main program. the expression *ptheta will denote the variable theta of the main program.. Hen e the statement p *pr=sqrt(x*x + y*y). *pa = *pb. The main program then resumes and will print the ex hanged values. The statement temp = *pa. We next onsider the swap program.e.3. Reasoning as before. out << x << `` ``<< y << endl. Thus our program will be ompiled orre tly. Here is the fun tion. having type int*. and the address of y into pb. be ause x and y are both 1. *pb = temp. Given that pr is of type float*.rst statement is *pr = sqrt(x*x + p y*y). the expression *pr denotes that float variable whose address appears in pr. The right hand side evaluates to 2.. But we pla ed the address of r of the main program in pr. will ause the value of x to be opied to temp.y are of type int. } It may be alled by a main program as follows. The address of x will be opied into pa. In the next statement. swap(&x. &y.&y). Next let us onsider the statement *ptheta = atan2(y. The fun tion all ompletes. The hanges required to the main program for mark averaging and the fun tion read marks into are left as exer ises.785 would get printed by the last statement in main. When the exe ution of main resumes.x are both 1. . 6 and 5.

2 we dis ussed the bise tion method for . the fun tions are easier to write with all by referen e. Whi h one is better? Clearly. Pointers You have seen that there are two ways of writing the fun tions Cartesian To Polar.3. Abhiram Ranade. Do not distribute 162 11.5 Referen e vs. 1 11. swap and read marks into. So that is learly to be re ommended in C++ programs. 2011.4 Fun tion Pointers In Se tion 7.

nding the roots of a mathemati al fun tion f (x). Figure 11. This ode ontains C++ equivalents of two mathemati al fun tions. we should have written the bise tion method itself as a C++ fun tion. Instead.2 shows how this an be done. to whi h you pass the mathemati al fun tion f (x) as an argument. f (x) = x 2. This was not how we wrote the method then. But we an do better now. and g(x) = sin(x) 0:3. The single fun tion bise tion is used to . Ideally. we presented ode for the method in whi h the ode for evaluating f (x) (not a all to it) was inserted as needed.

We will explain how bise tion works shortly. but .nd the roots of both these fun tions.

rst onsider the main program. As you an see. main alls bise tion for .

Consider the .nding ea h root.

The .rst all.

The last argument somehow supplies the fun tion f whose root is to be omputed.2. whi h gives the a eptable error in the fun tion value.0001. We are asking to . For this we have hosen the value 0. Exa tly why we need to write &f will be ome lear shortly.2. The next argument is epsilon.rst two arguments to the all are the left and right endpoints of the interval in whi h we know the fun tion hanges sign. The se ond all is similar.xR of Se tion 7. viz. instead of reading it from the keyboard. We have used the same endpoint values as xL. 0.

The last two lines merely print out the answers and he k if the square of the .0001.nd a root in the interval 0 to PI/2. again tolerating an error of at most 0.

3 First. On e we have a pointer to a fun tion. and the sine of the se ond answer is lose to 0. Thus C++ has the notion of a fun tion pointer.g. the expressions &f and &g are merely pointers to our fun tions f.rst answer is lose to 2. this parameter pf indeed appears dereferen ed. So all that remains to explain is how the fun tion bise tion will dereferen e and use them. we an identify a fun tion also by the address from where its ode starts. whi h you ould think of as the starting address of the ode orresponding to the fun tion. the key idea. Just as we an identify a variable by its starting address. As you know from Se tion 2. The name of the last parameter of bise tion is pf. ode and data are both pla ed in memory. We explain its ompli ated looking de laration soon. In the body. In the . we simply dereferen e it and use it! Thus.6.

So in other words. and some parameter is a referen e parameter.rst line it appears as (*pf)(xL). Also. 1 . how does the omputer know what variable the parameter refers to? A simple answer is: at the time of the all. and gets to the variables as needed. C++ automati ally sends the address of the variables referred to by the referen e parameters to the fun tion a tivation frame. during the fun tion exe ution. Noting that dereferen ing 2 Some of you are probably wondering: when a fun tion exe utes. C++ itself dereferen es the address of the referen e variables. where the parentheses are ne essary be ause just writing *pf(xL) will be interpreted as *(pf(xL)) whi h is not what we want. the operations of sending addresses and dereferen ing them that had to be manually written out in C are performed \behind the s enes" by C++.

3. float (*pf)(float x)) // pre ondition: f(xL). Do not distribute 163 float f(float x){ return x*x -2. int main(){ float y = bise tion(1.0. } float z = bise tion(0.f(xR) have different signs. { bool xL_is_positive = (*pf)(xL) > 0. ( >0 and <=0). // Invariant: f(xL).2: Bise tion method as a fun tion . if(xL_is_positive == xM_is_positive) xL = xM.2. Figure 11.&g). // Invariant: x_L_is_positive gives the sign of f(x_L). float epsilon. // maintains both invariants } return xL. float xR. out << "Sin inverse of 0. } float g(float x){ return sin(x) .0.0001.&f).f(xR) have different signs.0001. bool xM_is_positive = (*pf)(xM) > 0.3: " << z << " he k sin: " << sin(z) << endl. out << "Sqrt(2): " << y << " he k square: " << y*y << endl. Abhiram Ranade. } while(xR-xL >= epsilon){ float xM = (xL+xR)/2. // maintains both invariants else xR = xM. 2011. } float bise tion(float xL.0.PI/2.

Thus this ode will work exa tly like the ode in Se tion 7. Abhiram Ranade. the expression (*pf)(xL) will indeed evaluate to f(xL) when pf has value &f. Do not distribute 164 works exa tly as we expe t.2 for the . 2011. Similarly the expression (*pf)(xM) will evaluat f(xM).

So the only thing that remains to be explained now is the rypti de laration of the last parameter of bise tion.rst all. it does not make sense to pass a fun tion su h as g d (whi h takes 2 int arguments and returns an int). Basi ally we need a way to say that something is a fun tion pointer. Pointers to only ertain types of fun tions are a eptable as arguments to bise tion: spe i. Note however.

De laring pointers is somewhat tri ky and rypti .4. Perhaps the best way to read it is the reverse of what we did above. First. then we know from Se tion 9.1 Some simpli. Doing this we get what we wanted. float (*pf)(float).7.int arguments and returning float. Repla e *ph by h and observe that h must be a fun tion taking double.1 that it an be de lared as: float pf(float). ally pointers to fun tions that take a single float argument and return a float as result. this is how you would de lare ph to be a pointer to a fun tion whi h takes a double and int as argument and returns a float. then repla e v by *v and the new de laration will de lare v to be pointer to T . 11. It takes a bit of pra ti e to write su h de larations and even read them. To take another example. If the name of the fun tion is pf.int). Hen e *ph must be a pointer to su h a fun tion. // *pf is fun tion taking float and returning float // pf is pointer to fun tion taking float and returning float where the parentheses have been put to avoid asso iating * with float. float (*ph)(double. let us onsider how to de lare a fun tion that takes a float as argument and returns a float result. // pf is a fun tion taking float and returning float But now we simply note the general strategy for de laring pointers: if a de laration de lares name v to be of type T.

Unfortunately. If a parti ular parameter has a default value. the de laration of a fun tion pointer parameter. ations The C++ standard allows you to drop the operator & while passing the fun tion. and also the dereferen ing operator * while alling the fun tion. then the orresponding argument may be omitted while alling it. this does not help in the tri kiest part. 11. The default value is spe i.5 Default values of parameters It is possible to assign default values to parameters of a fun tion.

ed by writing it as an assignment to the parameter in the parameter list of the fun tion de.

. Here is a polygon fun tion in whi h both parameters have default values.nition.

Abhiram Ranade. i++){ forward(sidelength). } return. 2011. i<nsides. float sidelength=100) { for(int i=0. Do not distribute 165 void polygon(int nsides=4. right(360. } Given this de.0/nsides).

We an also make a all polygon() for whi h a square of sidelength 100 will be drawn. in whi h ase the nsides parameter will have value 4 and sidelength will have value 100. In general. if we wish to assign a default to the ith parameter. i. or by omitting both parameters. then a default must also be assigned to the i + 1th. we an make a all polygon(5) whi h will ause a pentagon to be drawn with side length 100.nition. so we may all polygon(8. we are allowed to all the fun tion either by omitting the last argument.e. In other words. Further. we an assign default values to any suÆx of the parameter list. and to a pre.120) whi h will ause an o tagon of sidelength 120 to be drawn. while alling we must supply values for all the parameters whi h do not have a default value. We are free to supply both arguments as before. in whi h ase the sidelength parameter will have value 100. i + 2th and so on.

In other words. if the .x of the parameters whi h do have default values.

then any all must supply values for the .rst k parameters of a fun tion do not have default values and the rest do.

6 Fun tion overloading C++ allows you to de. where j k.rst j parameters. 11.

but several. This omes in handy when you wish to have similar fun tionality for data of multiple types. Here is how you ould de. For example. you might want a fun tion whi h al ulates the g d of not just 2 numbers. provided the fun tions have dierent parameter type lists.ne multiple fun tions with the same name. say 3 as well as 4.

ne fun tions for doing both. in addition to the g d fun tion we de.

q). int q.g d(r. int g d(int p. You migth want to have an absolute value fun tions for float data as well as int. Here is another use.ned earlier. int r){ return g d(g d(p.r). int q. } int g d(int p. } The above fun tions in fa t assume that the previous g d fun tion exists. . int s){ return g d(g d(p.q). int r.s)). int Abs(int x){ if (x>0) return x. C++ allows you to give the name Abs to both fun tions.

The answer is simple: if your all is abs(y) where y is int then the . float Abs(float x){ if (x>0) return x. 2011. Abhiram Ranade. you may wonder how does the ompiler know whi h fun tion is to be used for your all. Do not distribute } 166 else return -x. } While it is onvenient to have the same name in both ases. else return -x.

7 Fun tion templates You might look at the two abs fun tions we de. 11. the right g d fun tion will be pi ked depending upon how many arguments you supplied. if the type is float then the se ond fun tion is used. Likewise.rst fun tion is used.

but the bodies are really identi al. A fun tion template does not de. ould we not just give the body on e and then have the ompiler make opies for the dierent types? It turns out that this an also be done using the notion of fun tion templates as follows.ned in the pre eding se tion and wonder: sure the fun tions work on dierent types.

ne a single fun tion. but it de.

nes a template. for de. or a s heme.

The template has a ertain number of variables: if you .ning fun tions.

and it will de. } The name T is the template variable. then you will get a fun tion! Here is an example. You an put in whatever value you want. else return -x. template<typename T> T Abs(T x){ if (x>0) return x.x the values of the variables.

float y=-4. Then C++ will reate two Abs fun tions for you. out << Abs(y) << endl. } out << Abs(x) << endl.ne a fun tion. On seeing the .6. In fa t C++ will put in the value as needed! So if you have the following main program int main(){ int x=3.

C++ will realize that it an reate an Abs fun tion taking a single int argument by setting T to int. Likewise T will be set to float and another fun tion will be generated for use in the last statement. . A more interesting example is given in the exer ises.rst out statement.

Do not distribute We . 2011. 167 Abhiram Ranade.

nally note that the fun tion template must be present in every sour e .

le in whi h a fun tion needs to be reated from the template. So a template is best written in a header .

So for a template fun tion f we will typi ally have a header .le. only the fun tion generated from the template is ompiled. Note also that the template itself annot be ompiled.

h.le f. but no .

Write a fun tion to . A key rule in assignment statements is that the type of the value being assigned must mat h the type of the variable to whi h the assignment is made. 2. Ea h of the assignments is in orre t.*y. *b. &x. z=3. write the ode in a program. 11. pp. *x. x y z y y = = = = = &b.8 Exer ises 1.le f. Can you guess why? If not. ompile it. Write the fun tion read marks into and the main program for mark averaging using pointers. b[3℄. and the ompiler will tell you! 3. y. Consider the following ode: int *x.

nd roots of a fun tion f using Newton's method. The k-norm of a ve tor (x. p 4. y. z) is de. It should take as arguments pointers to f and also to the derivative of f.

Note that the 2-norm is in fa t the Eu lidean length. However. The fun tion passed to the bise tion fun tion took a float and returned a float. Write a fun tion to al ulate the norm su h that it an take k as well as the ve tor omponents as arguments. You should also allow the all to omit k. the most ommonly used norm happens to be the 2 norm. we might well need to . Indeed. 5.ned as xk + yk + zk . in whi h ase the 2 norm should be returned.

k . Also. You an of ourse also do this by overloading the name bise tion.nd the root of a fun tion whi h takes a double and returns a double. Turn bise tion into a template fun tion so that it works for both double and float types. it would be ni e if the types of the other arguments were likewise made double.

i. Given the marks obtained by students in a lass. For example. determine their state 1 million years from today.e. here are some real life questions that we may be alled upon to answer: Given the positions. print out the marks in de reasing order.Chapter 12 Arrays Real life problems deal with many obje ts. the highest marks . velo ities and masses of stars.

rst. Given the road map of India .

If we want to write programs to solve su h problems using what we have learned so far. we would have to separately de.nd the shortest path from Varanasi to Buldhana.

This ee tively auses 1000 variables to be de. 12. Even writing out distin t names for variables to store data for ea h of these entities will be tiring. We might want to work with thousands of stars or hundreds of students or roads. Most programming languages in luding C++ provide the notion of an array so that we an onveniently and tersely deal with large olle tions of obje ts.ne variables for ea h star/student/road.1 Array: Colle tion of variables C++ allows us to write statements su h as: int ab [1000℄.

ned! The .

rst of these is referred to as ab [0℄. and ab [0℄. and so on till ab [999℄. Any identi. . The olle tion of these 1000 variables is said to onstitute the array named ab .. ab [1℄. ab [999℄ are said to onstitue the elements of the array.. next as ab [1℄..

1. The total number of elements (1000 in the above example) is referred to as the length or the size of the array. As we know. so the statement above reserves 1000 words of spa e in one stroke.er (Se tion 3. and not at 1 as you might be in lined to assume. It is important to note that indi es start at 0. What is inside [ ℄ is said to be the index of the orresponding element. 168 . an int variable needs one word of spa e. The term subs ript is also used instead of index.3) an be used to name an to array. The largest index is likewise one less than the total number of elements.

Abhiram Ranade. You may de. ab [2℄ following ab [1℄ and so on. is stored in memory following ab [0℄.e. Do not distribute 169 The spa e for an array is allo ated ontiguously. and onse utively by the index. i. 2011.

// array of 500 float elements.g. ab [1℄ float b[500℄. You an mix up the de.ne arrays of other kinds also. e.

nitions of ordinary variables and arrays. and also de.

x[10℄. double . y[20℄.ne several arrays in the same statement. z. This statement de.

z. Note that one variable of type double requires 2 words of spa e. 2 20 words for x. You may de. z of type double. so this statement is reserving 2 words ea h for .nes variables . 20. and respe tively 2 10.y. y also of type double and respe tively having lengths 10. and two arrays x.

Note however. that variables de.ne arrays in the main program or inside fun tions as you wish.

ned inside fun tions are not a essible on e the fun tion returns. This applies to arrays de.

int d = g d(a[0℄. // reads from keyboard into a[0℄ a[7℄ = 2. 12. a[b*2℄ = 234. int a[1000℄.1. // index: arithmeti expression OK In the .ned in fun tions as well.1 Array element operations Everything that an be done with a variable an be done with elements of an array of the same type. in >> a[0℄. // stores 2 in a[7℄.a[7℄). // g d is a fun tion as defined earlier. // b gets the value 10. int b = 5*a[7℄.

rst statement after the de.

But you an set the value of a variable also by assigning to it. The statement following that. b=5*a[7℄.nition of a. just as we might read into any ordinary variable. just as you might use an ordinary variable. This is also perfe tly . we are reading into the zeroth element a[0℄ of a.. as in the statement a[7℄=2. uses the element a[7℄ in an expression.

Elements of an array behave like ordinary or s alar variables of the same type. an element must have a value before it is used in an expression. When the ode is exe uted.a[7℄). assuming g d is a fun tion taking two int arguments. so they an be passed to fun tions just like s alar variables. This is a eptable. In other words. be ause a[8℄ has not been assigned a value. In the last line in the ode the index is not given dire tly as a number.ne. but instead an expression is provided. the value of the . that just like ordinary variables. if we wish. it would be improper in the above ode to write int b = 5*a[8℄. Hen e we an write g d(a[0℄. Note however.

In the present ase. So 234 will be stored in a[20℄. 170 Abhiram Ranade. 2011. by looking at the pre eding ode we know that b will have the value 10. For example. and hen e a[b*2℄ is simply a[20℄. for the array a are de. When using arrays in your programs. it is very important to keep in mind that the array index must always be between 0 (in lusive) and the array size (ex lusive). Do not distribute expression will be omputed and will be used as the index.

a referen e a[1000℄ would be in orre t. Unfortunately no error message will be produ ed in general. it will exe ute erroneously. Likewise. be ause it is really the referen e a[20000℄ given that b has value 10 in the ode above. If your program ontains su h referen es.2 Initializing arrays It is possible to ombine de.ned above. be ause it is not in the range 0 to 999.1. 12. a referen e a[b*2000℄ would also be in orre t.

0. 30. Suppose we wish to reate a 5 element float array alled pqr ontaining respe tively the numbers 15. 40.0. in whi h the size of the array is not expli itly spe i.0. 17.0. 40. 17.nition and initialization. In fa t. 12. 12. an alternate form is also allowed and you may write: float pqr[℄ = {15.0. We ould do this as follows. 12. 30.0. 40. 17.0}.0. float pqr[5℄ = {15. 30.0}.0.

You an of ourse mix de.ed. and it is set by the ompiler to the number of values given in the initilizer list.

nitions of arrays with or without initialization. and also the de.

squares of length 5. This will reate a single int variable x. 9. 16}. int x. it might be more onvenient to initialize arrays separately from their de. and two initialized arrays. and ubes of length 4.nition of variables. 1. 1. 8. squares[5℄ = {0. 4. 27}. Of ourse. ubes[℄={0.

times at whi h trains leave. i. e. xn . lengths of roads. xn. and then store xi in ith element of a length n array. You ould also say that an array is perfe t to store any sequen e x .1. So if we wanted a large table of squares. An array an also be used to store a ma hine language 1 2 0 1 1 . x . and so on.nitions. : : : . As will be dis ussed in Se tion 13. : : : . an array an be used to store text. velo ities of parti les. Note the slight pe uliarity of C++: it is better to name the sequen e starting with 0. it might be more onvenient to write: int squares[100℄ for (int i=0. i<100.e. marks obtained by students. i++) squares[i℄ = i * i. espe ially if they are large. x . all it x .g. 12.2 Examples The ommon use of arrays is to store values of the same type.

At this point. it is not supported by C++ and annot be used in programs.6). One way would be to put up a list on the s hool noti e board. Thus. This notation is only for onvenien e in dis ussions.2. Clearly we should use an array to store the marks. Can we write a program to do this? For simpli ity.. We will see many su h uses in the rest of this hapter and the following hapters. until the value -1 is supplied as the roll number. 12. Let us also stipulate that the program must print out the marks of ea h student whose roll number is entered. Do not distribute program: the ith element of the array storing the ith word of the program (Se tion 2. the marks of student with roll number 2 in the . and their roll numbers are between 1 and 100. You will see some standard programming idioms for dealing with arrays. let us assume that there are 100 students in the lass. the program must halt.1 Notation for subarrays It will be onvenient to have some notation to indi ate subarrays of an array. The tea her loads the marks onto a omputer. 2011. then the subarray is empty.2 A marks display program Suppose a tea her wants to announ e the marks the students in a lass have got. and the omputer displays the marks.j ℄ to mean elements A[k℄ of the array A where i k and k j . Note that if i > j . In this se tion we give some typi al examples of programs that use arrays. we will use the notation A[i. 171 Abhiram Ranade. It is natural to store the marks of the student with roll number 1 in the 0th element of the array. 12. Another possibility is as follows.2. Then any student that wants to know his marks types his roll number.

the marks of the student with roll number i in the element at index i 1.rst element. and in general. So we an de.

i<100. // marks[i℄ stores the marks of roll number i+1. 1 float marks[100℄. the then urrent value of i is used to de ide whi h element gets the value read. Hold that thought for a while. we will dis uss this issue in Se tion 12. You are probably wondering whether we need to hange the program if the number of students is dierent. Thus in the . for(int i=0.8. is exe uted.ne the array as follows. } Remember that when the statement in >> marks[i℄. i++){ out << "Marks for roll number " << i+1 << ": ". Next we read the marks into the appropriate array elements. in >> marks[i℄.

An exer ise asks you to add a password so that ea h student an only see her marks. and 1 Many might not like the idea of displaying marks in publi .rst iteration of the loop i will have the value 0. and so what is read will be stored in marks[0℄. In the se ond iteration i will have the value 1 and so the newly read value will be stored in marks[1℄. .

Do not distribute 172 so on. then you would want the marks for roll number 35. if(rollNo == -1) break. in >> rollNo. Abhiram Ranade. Thus indeed we will have the marks of a student with roll number i+1 be stored in marks[i℄ as we want. There are various ways to do this. similar to Se tion 6. 2011. marks[rollNo-1℄. Sin e this is to happen till -1 is given as the roll number. But this is exa tly the same element as what is printed. we learly need a while loop. students enter their roll numbers and we are to print out the marks for the entered roll number. and these would be stored in marks[34℄. int rollNo. In the last part of the program. if you typed 35 in response to the query \Roll number: \.3 while(true){ out << "Roll number: ". Clearly. } out << "Marks: " << marks[rollNo-1℄ << endl. we hoose one with a break. The program given above will work .

the program will attempt to read marks[999℄. int rollNo. in >> rollNo. be ause students oming later will then not be able to know their marks. Halting is not a eptable in this situation. then we an say so and not print any marks.3 Who got the highest? Our next example is a ontinuation of the previous one. and then print out the roll numbers of the student(s) who got the highest marks. We will assume for this part that the marks have already been read into the array marks. so long as the roll number given is either -1 or in the range 1 through 100. or worse. If the roll number is not in the given range. this may result in some irrelevant data to be read. while(true){ out << "Roll number: "." << endl. if(rollNo == -1) break. and as .ne. If a number other than these is given. the program may a tually halt with an error message. We want to read in the marks. 12. } if(rollNo < 1 || rollNo > 100) out << "Invalid roll number. So the ode should really be as follows. else out << "Marks: " << marks[rollNo-1℄ << endl. Fortunately we an easily prevent this. say 1000. As we said.2.

so that the length of marks is 100. In the . 2011. What we want an be done in 2 steps. Abhiram Ranade. Do not distribute 173 before assume that there are exa tly 100 students in the lass.

In Se tion 3.4.rst step we determine the maximum marks obtained. we print out the roll numbers of all who got the maximum marks.1 we have already dis ussed how to . In the se ond.

Basi ally. instead of reading from the keyboard. we are required to read them from the array. Now instead of getting the marks from the keyboard.nd the maximum of the numbers read from the keyboard. the .

we examine ea h marks[i℄. and subsequent elements by looking at marks[i℄. for all i as i goes from 0 to 99. float maxSoFar = marks[0℄. where i has to go from 1 to 100. i++){ if(maxSoFar < marks[i℄) maxSoFar = marks[i℄.rst element will be obtained from marks[0℄. i<100. The ode for this is as follows. } // i starts at 1 be ause we already took marks[0℄ The next step is to print the roll numbers of those students who got marks equal to maxSoFar. and whenever we . This is easily done. for(int i=1.

we a umulated (sometimes alled redu ed) the elements of the array using the operator max. and then we . for(int i=0. we print the index i.'' << endl. We have seen two ideas in this example. i<100. i++) if(marks[i℄ == maxSoFar) out << ``Roll number `` << i << `` got maximum marks. First.nd marks[i℄ equalling maxSoFar.

ltered out those elements whi h satis.

between 10 and 19 and so on till the ount of the numbers re eiving marks between 90 and 99. The 0th element of the array should ount for the range 0-9.ed the ondition that they equal the maximum value. the . how many between 20 and 29 and so on. We are required to report how many students got marks between 0 and 9. We are required to report 10 numbers. Again. the ount of the students re eiving marks between 0 and 9. we have as input the marks of students in a lass. 12. Assume for simpli ity that the marks are in the range 0 through 99. what we are asked to report is often alled a histogram in Statisti s . how many between 10 and 19.4 Histogram Our next example is tri kier. and it illustrates an important powerful aspe t of arrays. As you might know. So it ould seem natural to use an array of 10 elements.2.

So we ould all it ount and de. So in general we ould say ith element of the array should orrespond to the range i*10 to (i+1)*10-1 (both in lusive).rst element for the range 10-19 and so on.

10-19 and so on). in our ase) falling in various ranges of values (in our ase the intervals 0-9. In general a histogram is a ount of number of observations (marks.ne it as: 2 int ount[10℄. The ounts are often depi ted as a bar hart. 2 . // ount[i℄ will store the number of marks in the range // i*10 through (i+1)*10 -1. in whi h the height of the bars is proportional to the ount and width to the range.

and hange them as we read in the marks. else if(marks <= 79) ount[1℄++. 12.2. this is simply bm=10 . you assign the taxi that reported to you the earliest. . else if(marks <= 39) ount[1℄++. but there is a better way! Suppose we read a mark m. we should set the ounts to 0 at the beginning. how do we de ide whi h ount to in rement? It is natural to write something like the following. i++){ float marks.e. if(marks <= 9) ount[0℄++. As you might observe. int index = marks/10. for(int i=0. i. in >> marks. else if(marks <= 89) ount[1℄++. else if(marks <= 49) ount[1℄++. for(int i=0. Do not distribute 174 Clearly. When we read the next mark." << endl. if(index >= 0 && index <= 9) ount[index℄++. else out << "Marks are out of range. i++){ float marks. else if(marks <= 59) ount[1℄++. else if(marks <= 19) ount[1℄++. 2011. else if(marks <= 99) ount[1℄++. in >> marks. But this is very often the ase when omputing histograms. else out << "Marks are out of range." << endl. Passengers who want taxis also report to you. whi h ount should we in rease? For this we simply need to know the tens pla e digit of m. i++) ount[i℄=0. Your job is as follows. the integer part of m=10. But we an get the integer part by storing into an integer variable! Whi h is what the following ode does. i< 100. else if(marks <= 69) ount[1℄++. } Note that this works only be ause all the ranges are of the same size. } This works. i< 100. You he k if there are any waiting taxis. else if(marks <= 29) ount[2℄++. If so. Drivers of taxis that are willing to take passengers to Pune report to you and give you their phone numbers and wait. i<10.5 A taxi dispat h program Suppose you are the Mumbai dispat her for the Mumbai-Pune taxi servi e. for(int i=0. Abhiram Ranade.

though an exer ise asks you to do pre isely this. Dispat hing without omputers It is always worth thinking about how any problem. and that number is erased. on e a taxi has been given to a passenger. you need not keep the orresponding phone number on your list. You are not expe ted to keep tra k of waiting passengers. Say the dispat her writes the phone numbers on a bla kboard. If no taxis are available. in luding taxi dispat hing. Sin e we do not expe t there to be more than 100 waiting drivers at any time. Abhiram Ranade. might be solved without omputers. Do not distribute 175 Clearly. You are to write a program whi h will help you dispat h taxis as required. You may assume that at any given point there will not be more than 100 taxis waiting for passengers. the number at the top of the list is given to the passenger. you let the passenger know. we should be . When a passenger omes in. 2011. as the drivers report. top to bottom.

but they start halfway down the board. and you write down their numbers. that managing the spa e on the bla kboard is tri ky. whi h you erase.ne if the the bla kboard is large enough to hold 100 numbers. and we will hoose one of those possible ways. you have 70 numbers on the board. This is not stri tly ne essary. and that would take you to the bottom of the board. They begin at position 50 (the topmost position being 0). Note however. You would pla e 40 of these numbers below the 10 you have on the board. as if the bottom of the board were joined to the top. we will use an array board of int. Where should you pla e the remaining 20? It is natural to start writing numbers from the top again. the top of our list and its bottom (likely wrapped around). This way. go to the last position. Dispat hing using omputers Our program will mirror the a tions given above. Suppose now 60 more drivers report. We will also argue why our book keeping is orre t. of size n = 101. At this point you have only 10 numbers on the board. however. Positions 20-49 are then unused. starting at the top. The book keeping an be done in many ways. Then they \wrap around" so that the last 20 numbers o upy positions 0 through 19 on the board. In prin iple. Think of the bla kboard as forming the urved surfa e of a ylinder! Thus at this point. But there is some amount of book keeping we need to do orre tly. Suppose you next have 50 passengers. even if 100 drivers appear. will be separated by one spa e. 99. they are not at the top of the board. this is not diÆ ult. but we . This will be useful be ause there are many opportunities of making mistakes in the book keeping! To model the board. Suppose 60 drivers report. so you mat h them to the top 50 numbers.

and emptyEnd whi h gives the last index of the unused portion. we annot assign sensible values to top and bottom. Clearly. emptyBegin whi h gives the starting index of the unused portion of board. as happens at the beginning. that there are no waiting drivers.nd it onvenient for making the argument. The most natural way to do this is to have int variables top and bottom whi h respe tively give the indi es at whi h the list of numbers begins and ends. So we will maintain two int variables. we must keep tra k of the indi es orresponding to the top and the bottom of the list. In this ase. It is possible. though. So we will instead keep tra k of the portion of the board that is unused. For these names .

176 Abhiram Ranade. In these . as shown in Figure 12. Initially. 2011. Do not distribute emptyBegin 0 1 0 1 0 1 Occupied by numbers Unused emptyBegin emptyEnd Occupied by numbers Unused Unused emptyBegin emptyEnd Unused emptyEnd n −1 (a) At the beginning n −1 Occupied by numbers n −1 (b) After some time (a) After more time Figure 12. we must have at least one unused element at all times. So having an array of size n = 101 will indeed prove useful.1(a). we will set emptyBegin = 0 and emptyEnd = n-1.1: Snapshots of the board to be assigned sensibly.

numbers may be written and erased. and the board on. the index at whi h these names appear is to be onsidered as their value. As time goes by. On the right side of the re tangle we have written down the names emptybegin and emptyEnd.gures ea h re tangle s hemati ally denotes an array in memory. On the left side of the re tangles we have written down the indi es of the elements at that height in the re tangle.

guration may ome to resemble parts (b) and ( ) of the .

(2) The unused indi es o upy the region from emptyBegin to emptyEnd. indeed if some element (emptyBegin + k) % n equals n-1. . Thus our invariants are: (1) There is at least one unused index at all times. The ode is easy to write if we adhere to the interpretation we gave to the variables emptyBegin and emptyEnd. wrapping around if ne essary. The key point is that the unused portion an span over the end of the array and ontinue down from the top (Figure 12. . More pre isely.1(b)). then (emptyBegin + k + 1) % n equals 0. the unused portion orresponds to the indi es in the following sequen e: emptyBegin. or may be ontiguous within the array (Figure 12. .1( )).gure. (emptyBegin + 1) % n. Note that these onditions are satis. (emptyBegin + 2) % n.. emptyEnd Note that by taking the remainder mod n our sequen e wraps around from the bottom to the top.

Next we onsider what a tions to exe ute when a driver arrives. If we a ept the phone number. then it will redu e the size of the unused region.ed by the values we assigned at the beginning: we set emptyBegin to 0 and emptyEnd to n-1. the largest index. But our .

rst ondition requires .

If they are indeed equal.\n". out << "Assigning " << board[emptyEnd℄ << endl. When a ustomer arrives. in board[emptyBegin℄. int board[n℄. Thus this must happen modulo n. Abhiram Ranade. The program must handle two kinds of requests: arrival of a taxi. we annot register the driver. while(value>=0){ // exit on negative value if(value > 0){ // driver registering. then we annot a ept the phone number. else{ emptyEnd = (emptyEnd + 1)% n. int value. Do not distribute 177 that the unused region size not go to zero. The program is as follows. Suppose a passenger arrives. Then the program must print out the phone number of the driver of the longest waiting taxi. If the ondition is false. But this happens only if emptyBegin equals emptyEnd + 1 modulo n. We must assign a taxi if one is waiting. again modulo n to ensure wrap around if needed. Otherwise.e. if(emptyBegin == emptyEnd) out << "Cannot register. A taxi must be waiting unless the unused portion o upies the entire array. we store the phone number at the beginning of the empty region. our dispat her simply type in the driver's phone number. and we print a message to that ee t. } } else if(value == 0){ // ustomer requesting if(emptyBegin == (emptyEnd+1) % n) out << "No taxi available. we de line the passenger's request. int main(){ onst int n=101. we assign the earliest waiting driver.\n". we will require that when a taxi arrives. The earliest waiting driver must be the one just beyond the end of the unused list. But the unused area has size 1 if and only if emptyBegin and emptyEnd are equal. For simpli ity. i. } . Next we in rement emptyBegin. in >> value. 2011. the one in board[(emptyEnd+1)%n℄.e. So we assign this to the ustomer and in rement emptyEnd. This must be pla ed into our array if possible. emptyBegin = (emptyBegin + 1) % n. If it is true. the dispat her types in 0. i. and arrival of a passenger. The program We now onsider the remaining details. So we he k this ondition. and we assume that no phone number an be 0. wrapping around if ne essary. } } in >> value. else{ board[emptyBegin℄ = value. emptyEnd=n-1. emptyBegin=0. So if the size of the unused area is exa tly 1 before the driver arrives.

Do not distribute } We have written this program so that it an run ad in. 2011. 178 Abhiram Ranade.

Here is how we an do this.nitum. where of ourse i 6= j . Spe i. Our goal is to determine whether any of the ir les interse t. Whether a pair of ir les interse t is easy to he k: the ir les interse t if and only if the distan e between their enters is smaller than or equal to the sum of their radii. But it will stop with a message if you type in a negative value. Let us say that the ith ir le has enter (xi . yi ) and radius ri . In other words.r in whi h we will store the x.6 A geometri problem Suppose we are given the positions of the enters of several ir les in the plane as well as their radii. : : : . 12. n 1.y oordinates of the enter and the radius of the ir les. j . for i = 0.2. Thus. in our program we must ee tively he k whether this ondition holds for any possible i. We will use arrays x.y. ir le i and ir le j interse t if and only if: q (xi xj )2 + (yi yj )2 r i + r j Or equivalently (xi xj ) +(yi yj ) (ri + rj ) .

the y oordinate in y[i℄.y) = x raised to y.i++) // read in all data. ally. // oordinates of enter of ea h ir le. for(int i=0. i<n. j<n. y[n℄. 2 #in lude <novi e pp> main(){ int n=5. float r[n℄. and the radius in r[i℄. the x oordinate of the enter of the ith ir le will be stored in x[i℄. We will then he k whether ea h ir le i interse ts with a ir le j where j>i. // radius of ea h ir le." <<endl.2)) // built in fun tion pow(x. i++){ for(int j=i+1.2)+pow(y[i℄-y[j℄. for(int i=0.i<n. } } Thus in the . in >> x[i℄ >> y[i℄ >> r[i℄. j++){ if(pow(x[i℄-x[j℄. 5 hosen arbitrarily.2) <= pow(r[i℄+r[j℄. float x[n℄. 2 2 // number of ir les. out << "Cir les " << i << " and " << j << " interse t. // Find interse tions if any.

n 1. k + 2. we he k for interse tions between ir le 1 and ir les 2. we will he k interse tions with ir les k + 1. . In the se ond iteration. Can we be sure that the interse tion between them is he ked? Clearly. 2. Is this lear that we he k all pairs of ir les in this pro ess? Consider the kth ir le and the lth ir le. k 6= l. n 1. : : : . we he k for interse tions between ir le 0 and 1. : : : . n 1.rst iteration of the outer for loop. : : : . 3. then in the iteration of the outer for loop in whi h i takes the value k. and so on. if k < l. 3.

Do not distribute 179 This sequen e will ontain l be ause k < l.3 The inside story We would like to larify some details regarding arrays and array a esses. Alternatively. for every k. 12. Clearly k will be in this sequen e be ause l < k. In this iteration we will he k the interse tion of ir le l with ir les l +1. suppose l < k. Thus in either ase we will he k the interse tion between ir le k and ir le l. Abhiram Ranade. Then onsider the iteration of the outer for loop in whi h i= l. : : : . n 1. l. 2011. This will spe ially be useful for understanding how we de.

ne fun tions for operating on arrays. suppose we have the following de. To make the dis ussion more on rete.

13. q[5℄={11.12. float s[10℄.15}.14. Thus we know the above de. and so is a float. int p=5. Say ea h variable of type int is most ommonly given 4 bytes of memory.nitions. r=9.

The notion of addresses is as per our dis ussion in Chapter 2. and go on to address Q +19. and 4 10 = 40 bytes for s. How does the omputer know where this element is stored? Of ourse. Next we onsider what happens when during exe ution we en ounter a referen e to an array element. Thus. 4 for r. say Q. 4 5 = 20 bytes for q. Figure 12. . Consistent with this des ription. We have also said that the memory given for an array is ontiguous.3 shows how spa e might have been allo ated for these variables. q[expression℄.nitions will ause 4 bytes of memory to be reserved for p.g. e. the memory for q will start at a ertain address.

where k is the number of bytes needed to store a single element. Then we know that we want the element of q of index v. Do note however that the extra work needed to . the v th element of an array whi h is stored starting at address A would be at A + kv. But be ause the elements are stored in order. This is in ontrast to how the omputer gets the address for an ordinary variable su h as p. Suppose its value is some v. and so it an get to it dire tly. the omputer already knows where it stored p. So the important point is. whi h is stored from Q + 12. Thus if v = 3 then we would want q[3℄. that to get to an array element. where Q is the starting address for q. the omputer must evaluate the index expression. In this ase. and even after the expression is evaluated it must perform the multipli ation and addition to get the address A + kv. we also know that the element with index v is stored at Q + 4v. In general.rst the expression must be evaluated.

3.gure out where the element is stored is independent of the length of the array. 12.. Going as per the de.1 Out of range array indi es Suppose now that our program has a statement q[5℄=17.

Suppose on the other hand. that r is given the memory Q + 20 through Q + 23. Then the statement q[5℄=17 might end up hanging r! Likewise it is on eivable that a statement like q[-1℄=30. Noti e that this is outside the range of memory allo ated for q. In fa t. This would require us to a ess address Q + 40000. It is on eivable that there isnt any memory at this address. as shown in our layout of Figure 12.3. we would try to store 17 in the int beginning at the address Q + 20. we wrote q[10000℄=18..nition above. it is quite possible. might end up hanging p. Many .

Do not distribute Address Allo ation Q 5 ::: Q 4 Q 3 p Q 26 Q 1 Q Q+1 q[0℄ Q+2 Q+3 Q+4 Q+5 q[1℄ Q+6 Q+7 Q+8 Q+9 q[2℄ Q + 10 Q + 11 Q + 12 Q + 13 q[3℄ Q + 14 Q + 15 Q + 16 Q + 17 q[4℄ Q + 18 Q + 19 Q + 20 Q + 21 r Q + 22 Q + 23 Q + 24 Q + 25 s[0℄ Q + 26 Q + 27 Q + 28 ::: Figure 12. 2011.2: Possible layout 180 . Abhiram Ranade.

2011. 181 Abhiram Ranade. 12.3. It turns out that C++ allows this.2 The array name by itself So far we have not said whether the name of an array an be used in the program by itself. Do not distribute omputers have some ir uits to sense if an a ess is made to a non-existent address or even some forbidden addresses. then the program might halt with an error message.e. it is most important to ensure that array indi es are within the required range. In C++. the name of an array by itself is de. i. The details of this are outside the s ope of this book. without spe ifying the index. but if this happens. In any ase.

and that of s. Sin e the variable at address Q is q[0℄. it is natural to de. Q + 24. Thus the value of q would be Q.3.ned to have the value equal to the starting address from where the array is stored. of type int. assuming the layout is as per Figure 12.

su h as X[Y℄ to be an expression. or int*. and would have the value Q + 24.3 [℄ as an operator A further tri ky point is that C++ onsiders a referen e to an array element.ne the type of q to be pointer to int.Y the operands. and [℄ the operator! The operation is de. or address of int. and its utility will be ome lear in Se tion 12. This is merely a matter of onvenien e. It seems strange that the name of an array is only asso iated with the starting address.3. and that the length of the array is not asso iated with the name.4. 12. Analogously s would then be of type address of float or pointer to float or float*. with X.

Suppose that X is of type address of type T. v the value of Y. and Y is an expression that evaluates to a value of type int. and Y does evaluate to int. where A is the value of X. You will realize that we are merely restating how we . and k is the number of bytes needed to store a single element of type T. Then the expression X[Y℄ denotes the variable of type T stored at the address A + kv.ned only if X has the type \address of some type T".

Suppose we have an array of oats de. it ould be any name whose type is \address of some type T". But the restatement is more general: X does not need to be the name of an array.nd the element given the name of the array and the index. 3 12.4. and indeed we an imagine that they will be onvenient with arrays as well.4 Fun tion Calls involving arrays Fun tions are onvenient with ordinary. This generalization will ome in useful in Se tion 12. or s alar variables.

For example. But do note that there are other operations whi h are not written in the order operand1 operator operand2.ned as float a[5℄. however. this is an unusual way of writing a binary expression. 3 a b . if the sum is needed for several su h arrays in our ode. we often write ab rather than . Of ourse we an write ode to ompute the sum. then will have to repli ate the ode that many times. So it would Yes. and somewhere in the program we need to al ulate the sum of its elements.

1.0. int n){ float s = 0.0. i<n.0. asum. // se ond argument should be array length } Let us . i++) s += v[i℄.0}. 2011. } return s.0. Abhiram Ranade. 5). 3. for(int i=0. 4. Here is how the fun tion ould be written: float sum(float* v. 5. Do not distribute 182 be very onvenient to write a fun tion whi h takes the array as the argument and returns the sum. main(){ float a[10℄ = {0. asum = sum(a.0. This fun tion ould be alled using a main program as follows. 2.

whether the types of the arguments mat h those of the parameters in the de. i.rst he k whether the fun tion all is legal.e.

nition in the fun tion sum. The .

rst argument to the fun tion all is the array name a. We said that the type asso iated with the array name is \address of a variable of the type in the de.

nition of the name". in other words the type of a is address of a float. This indeed mat hes the type of the .

rst parameter in the fun tion de.

and so the values of both arguments are opied. In the present ase. The values of the non-referen e arguments are opied. as usual an area is reated for exe ution of the fun tion sum. 5.nition. learly has type int whi h mat hes the type of the se ond parameter n. The value of the . 5) is en ountered. Thus the all is legal and we now think about how it exe utes. When the all length(a. The se ond argument. none of the parameters are referen e parameters.

1. Thus v gets the value A and n the value 5. This is pro essed essentially a ording to the rule given earlier. in this ase arrays of float variables: float v[℄ { this dire tly suggests that v is like an array ex ept that we do not know its length. The value of the se ond argument is 5. It is very important to note here that the ontent of all the lo ations in whi h the array is stored are not opied. So now the expression v[i℄ is evaluated as dis ussed in the previous se tion. we merely note that the value of v[i℄ evaluated in sum must be the same as the value of a[i℄ evaluated in the main program. . v[i℄ will in fa t denote the ith element of a. be ause v has the same value and type as a. The ode of the fun tion is then exe uted. Instead of doing the pre ise al ulation again. Be ause n has value 5. a is the starting address. Another syntax an also be used to de lare parameters that are arrays. Thus a[0℄ through a[4℄ will be added as we desired. and its value is A. Some remarks are in order. We know that v has type address of oat.rst argument. The only new part is the expression v[i℄. Hen e. but only the starting address is opied. by onsidering [℄ to be an operator and so on. in the loop i will take values from 0 to 4. say A.

2011. Fun tion sum does not really know that it is operating on the entire array. For example the all sum(a. This would return the sum of the . Abhiram Ranade.3) is also allowed. Do not distribute 183 2.

3. and so when the all exe utes. sin e the loop in the fun tion will exe ute from 0 to 2. The array name is not passed as a referen e parameter. that using the [℄ operator the ode in the fun tion an refer to the array de. This has the ee t. the value of the array name is opied into the orresponding parameter.rst 3 elements of a.

ned in the main program. We had said earlier that ode in the fun tion annot refer dire tly to variables de.

through the passed address. However.ned in the main program. the value of the orresponding argument is not ae ted.. If your fun tion had a line at the end su h as v[0℄=5.4. that would indeed hange a[0℄. Thus if you hoose to modify v by storing a dierent address into it (not re ommended at all in the present ir umstan es!). Our . This is onsistent with the me hanism we have dis ussed for evaluating expressions involving [℄. sin e they are two distin t opies. 12.1 Examples Shown below are two simple examples of fun tions on arrays. the ode in the fun tion an refer to the array indire tly. If the value of a non-referen e parameter to a fun tion is hanged in the fun tion. Modifying the passed array is also possible. 4. The next se tions gives more involved examples. you will not hange the value of the orresponding argument a.0. be ause we are passing the address.

i++) out << a[i℄ << endl. int n){ for(int i=0. } This will print out the .rst fun tion merely reads values into a float array. i< n. void print(float *a.

and we are returning only one of them. and that the array has length at least as mu h as the se ond argument. Note the areful phrasing of the last senten e: when we say \an element". The idea of the fun tion is very similar to what we did for . we a knowledge the possibility that there ould be many su h elements. Here is a fun tion whi h returns an index of an element whose value is the maximum of all the elements in the array.rst n elements of the array. Note that it is the responsibility of the alling program to ensure that the an array is passed.

whi h is equivalent to onje turing that the maximum appears in position 0. We start by initializing it to 0.3. if we . we he k if the subsequent elements of the array are larger.nding the maximum marks from the marks array in Se tion 12.2. Next. We have a variable maxIndex whi h will return the position of an element with the maximum value.

int length) // marks = array ontaining the values .nd an element whi h is larger. int argmax(float marks[℄. then we assign its index to maxIndex.

Surely then B will be able to write to A or visit A just as you an! Finally.3. This is to be expe ted. the name of the array. But by itself this fun tion does not have anything to do with marks. Abhiram Ranade. Do not distribute 184 // length = length of marks array. 12. it may be onvenient to allow it to be alled with length spe i. required > 0.length-1℄ { int maxIndex = 0.4. When we write a fun tion on arrays. To pass an array to a fun tion. it is worth noting an important point. So the array length is needed. // returns maxIndex su h that keys[maxIndex℄ is largest in keys[0. j++) if( marks[maxIndex℄ > marks[j℄) // bigger element found? maxIndex = j. } We have given the name marks so that it is easy for you to see the similarity between this ode and the ode in Se tion 12.. This is like sending the address of one friend A to another friend B.2 Summary The most important points to note are as follows. 2011. for(j = 1. we must typi ally pass 2 arguments. The alled fun tion an read or write into the array whose name is sent to it. So if you write it independently some more appropriate name su h as datavalues should be used instead of the name marks. and the length of the array. it does not say how long the array is. // update maxIndex. return maxIndex.2. the name only gives the starting address of the array. j<length.

In fa t we will do this in two ways.ed as 0. however. This allows us to use the following two phase strategy. This is what our sum fun tion does. On the other hand. 12. print them out in the order highest to lowest. In the . this is left for the exer ises. In this se tion. we will ignore the fa t that the marks stored at index i are the marks obtained by the student with roll number i.5 Sorting an array We will onsider a problem dis ussed at the beginning of the hapter: given the list of marks. whi h will illustrate some ideas about passing arrays to fun tions. we also print out the roll numbers. We ould ask that along with the marks. Su h (pre) onditions on a eptable values of parameters should be learly stated in the omments. What should a fun tion su h as sum to when presented with an array of zero length? It would seem natural to return the sum of elements as 0. our argmax fun tion requires that the length be at least 1.

we rearrange the element values so as to ensure that the values appearing at lower indi es are no smaller than those appearing at larger indi es. This operation is often alled sorting. We will present a simple algorithm for this. On e the elements are arranged so that the larger ones appear before the smaller .rst phase. Better algorithms will be given in later hapters. This is one of the most important operations asso iated with an array.

Do not distribute 185 ones. we an simply print out the array elements by index. Abhiram Ranade. 2011.e. then element 1 and so on. For this. element 0. i. This will ensure that the marks are printed in non in reasing order. we an simply use the fun tion print de.

So we instead ex hange the two: the maximum value moves to the 0th position and the value in the 0th position moves to wherever the maximum was present earlier. we .ned earlier. and we move it to the position (index) 0 in the array. Of ourse. and we annot destroy that. We begin by looking for the largest value in the array. Next. We use a fairly natural idea for sorting. position 0 itself ontains a value.

We go on in this manner.nd the maximum value amongst elements in position 1 through n 1. where n is the array length. This maximum is ex hanged with the element in position 1. Thus we have the maximum and se ond maximum in positions 0 and 1. The basi operation in our algorithm is then the following. We need to .

i < n.n-1℄ and move // it to m[i℄. The value at m[i℄ will move to where the maximum was. i++){ if(m[i℄ > maxSoFar){ maxSoFar = m[i℄. We will write a fun tion for doing this. { int andidate = i. void sort(float data[℄. } } } marks[ andidate℄ = marks[i℄. All that remains now is to use this fun tion. The fun tion will have to take as arguments the name of the array. and the starting index i. i<n. marks[i℄ = maxSoFar. for(int i=1. int n. { for(int i=0. We an then write the fun tion to sort an array as follows. the length n.. i++) largest_of_i_to_last_moves_to_i(data. n. void largest_of_i_to_last_moves_to_i(float *m. say m. andidate= i. and ex hange that with the element at position i.nd the largest among the elements in positions i through n 1. int i) // This will find a maximum value in the region m[i. As you an see. There are two dieren es. i). int n) // will sort the array data of length n in non-in reasing order. we only need to onsider the array starting at a given index i. We must all it with dierent values of i. // ex hange the values. and at the end we must perform the ex hange. // index of andidate int maxSoFar = m[ andidate℄. this is simply a minor extension of the fun tion argmax that we wrote earlier. } .

e. we are asking that the maximum value in the elements of the array starting at data[n-1℄ through data[n-1℄ be pla ed at data[n-1℄. Do not distribute We have to be areful in alling the fun tion move largest to i { is the all in the last iteration orre t? In the last iteration. our fun tion works . 186 Abhiram Ranade. the value of i is n-1. Fortunately. 2011. i.

note that the last all is not ne essary.e. So the ode given above is not in orre t. Our se ond method is more subtle. However.ne even if i and n have the same value. We . i. the he k in the for loop might as well have been i<n-1 rather than i<n.

whi h uses the argmax fun tion de.rst present the ode.

i--){ int maxIndex = argmax(data.4. int n) // will sort in NON-DECREASING order. we are alling it with su essively smaller values. i>1. As we dis ussed earlier. } } different from above. float maxVal = data[maxIndex℄. this is a eptable. { for(int i=n. The most noteworthy point of this ode is the all to argmax. void sort2(float data[℄.i).1.ned in Se tion 12. data[i-1℄ = maxVal. the fun tion argmax will only onsider the . data[maxIndex℄ = data[i-1℄. Even though the length of the array data is n.

So in the .rst i elements of the array. in ea h invo ation.

we .rst iteration.

whi h in the .nd the index of a largest element. The 3 lines after the all to argmax merely ex hange the values of the maxindexth element (as returned by argmax) and the i-1th element.

rst iteration is simply the last element of the array. Thus at the end of the .

Thus in the se ond iteration. This we need to do until i be omes 2. but with a smaller value of i. we will have moved the se ond largest element to the position i-1. whi h in the se ond iteration has value n-2. In the next iteration.rst iteration. argmax will be asked to . be ause when i=1. a largest element has moved to the end of the array. we repeat the pro ess.

The situation is dramati ally dierent if the array is sorted. Suppose we have an array in whi h we have stored numbers. in the . we will know that only after looking at every element. sorting helps in performing ertain kinds of operations very fast.6 Binary sear h We often sort data be ause it looks ni e to print it that way. it ould be at any index in the array. and this is unne essary. 12. Instead of examining elements from the beginning of the array. If x is not present. we will need to go over ea h element in the array and he k if it equals x. Suppose now that we want to determine if a given number x is present in the array. on the average we ould say that we would examine about half the elements. In the worst ase we might still have to examine every array element. If x is present. Obviously. However.nd the maximum of (what it thinks is) an array of length 1.

rst step we examine the element that is .

2011. Abhiram Ranade. Then in the . Say our array is A and it ontains size elements. Do not distribute 187 roughly in the middle of the array.

.size-1℄ will also be larger than x. the value of size/2 rounded down. There are 2 ases to onsider.size/2-1℄. we have narrowed our sear h to the . Hen e x. The he k su eeds i. Now be ause the array is sorted.e. if present in the array.rst step we he k if x < A[size/2℄.. x is smaller than A[size/2℄. will be in the portion A[0. we know that all elements in the subarray A[size/2+1. Thus using just 1 omparison. Here we mean integer division when we write size/2. i.e.

half). This an be proved as follows. The \. then we should not try to halve it! In this ase we merely he k if the element equals x and return the result of the omparison. start whi h says where the subarray starts.. A[size/2. Thus the subsequent sear h needs to be made only in A[size/2. we have ensured that subsequently we only need to sear h in one of the halves of the array. Thus in both ases. int start. int size){ // x : target value to sear h // range to sear h: A[start. A. size-half). we know that the values in A[0. So we are sear hing in the region A[start. bool Bsear h(int x.e. be ause this region is known to ontain x. if(x < A[start+half℄) return Bsear h(x. But we an re urse on the halves! The key question is: when does the re ursion end. int half = size/2.. start.start+size-1℄. Clearly. // if(size == 1) return (A[start℄ == x). // re urse on se ond half. x is greater of equal to A[size/2℄. // 0 < half < size. after one omparison.e. (ii) A[size/2℄ equals x. start+half. we an make the subsequent sear h in A[size/2. if our array has only one element.. In this ase. // re urse on first half else return Bsear h(x. be ause size>1.size-1℄. In this ase..size/2-1℄ will be stri tly smaller.size-1℄. } There is an extra parameter. int A[℄. The he k fails i. A.start+size-1℄ // pre ondition: size > 0. The \middle" element now is A[start+size/2℄ whi h is the same as A[start+half℄ in the ode. we an narrow our sear h to the se ond half.. There are two ases to onsider: (i) A[size/2℄ is stri tly smaller than x. i. In this ase also. This gives us the following re ursive fun tion.rst half of the array..size-1℄..

Thus we have the re ursive alls in the fun tion. 2. 10. int A[size℄={1. 30}. Here is a main program whi h tests the fun tion. main_program{ onst int size=10. 2.rst half" starts at A[start℄ and has size equal to half. . 15. 15. The \se ond half" starts at A[start+half℄ and has size half. 28. 25. 3.

A. but ontains repeated values. i++) out << A[i℄ << " ". Do not distribute 188 for(int i=0. i<size. x++) out << x << ": " << Bsear h(x. You will see that 1 is returned only for those integers that are a tually present in the array. out << endl. for(int x=0. 2011.1 Time required Let us analyze a bigger example. x<=40. Suppose we are he king for the presen e of a number in an array of size 1024.6. size) <<endl. 12. How many array elements do we ompare in the pro ess? The fun tion binsear h will . } We sear h for presen e of all integers between 0 and 40. 0. Abhiram Ranade. Noti e that the array is sorted.

In ea h all we make only one omparison x < A[start+half℄.2) for . Thus a total of 10 alls will be made: in the last all size will be ome 1 and we will return the answer. A tually. You will see that it will appear in many pla es. without re ursion. and hen e only 10 omparisons will be made! Compare this with the ase in whi h the array is not sorted: then we might have to make as many as 1024 omparisons! Even if we agree that it takes a bit longer to all a fun tion. we will next all binsear h with size 512. no matter how the omparison omes out. perhaps slightly disguised. Subsequently we all binsear h with size 256 and so on. When we re urse. our binary sear h an be written out as a loop.rst be alled with the size parameter equal to 1024. whi h is mu h larger! Binary sear h is a simple but important idea. In general you an see that the number of omparisons made is simply the number of times you have to divide the size so as to get the number 1. the exer ises ask you to do this. This number is log(size). For the unsorted ase we might make as many as size omparisons. as it did in the Bise tion algorithm (Se tion 7. alling binsear h 10 times (in luding the re ursion) will be mu h faster than exe uting a loop to do 1024 omparisons.

say the entries of a matrix. then we will need two dimensional arrays. use a one dimensional array. 12. whi h is what we have studied so far. 4 . an . whi h we will see later. If a olle tion of mathemati al obje t is des ribed using two subs ripts. n i A polynomial A(x) = i aix is ompletely determined if we spe ify the oeÆ ients a .7 Representing Polynomials A program will deal with real life obje ts su h as stars. : : : . or roads. This most onveniently done in an array. Thus to represent the above polynomial we will need to store these oeÆ ients. How to represent polynomials on a omputer andPiperform operations on them are therefore important questions. or a olle tion of ir les. We use an array a of length n and store ai in = =0 0 1 1 4 There is a simple rule here { if a olle tion of obje ts is des ribed using one subs ript. It might also deal with mathemati al obje ts su h as polynomials.nding roots.

D(x) obtained by adding and multiplying A(x). B (x) respe tively? We know that i = ai + bi. Do not distribute a[i℄. suppose we have two arrays representing two polynomials A(x). 2011. Can we onstru t the representation of the polynomials C (x). 189 Abhiram Ranade. It is natural to ask. Next omes the question of how we operate on polynomials. B (x). Thus the array that we an use to represent the polynomial C (x) must be de.

but this array annot be returned ba k { it gets destroyed as soon as addp . its value an be assigned using the following ode: for(int i=0. i++) [i℄ = a[i℄ + b[i℄. Further.ned as float [n℄. Can we write a fun tion addp whi h adds two polynomials? The polynomials to be added will be passed as arguments. What about the result polynomial? We ould allo ate a new array inside the fun tion addp. i<n.

i<n. void addp(float a1[℄. result. float a2[℄. [5℄. The produ t an have 2n 1 oeÆ ients. i<5. for(int i=0. i++) in >> a[i℄ >> b[i℄.nishes exe ution. i<5.5). i++) r[i℄ = a1[i℄+a2[i℄. The orre t way to write this pro edure is to pass the result array as well. length of the arrays.b. i++) out << [i℄ << endl. b[5℄. addp(a. int n){ // addends. } for(int i=0. Thus it will have to be de. float r[℄. We will likewise use an array d to represent the produ t D(x). . } main(){ float a[5℄. for(int i=0. Here is a program whi h in ludes the fun tion addp.

we need to .ned as float d[2*n-1℄. To assign values to its elements.

i<2*n-1. for(int j=0. j<n. ea h term aj xj in the former will be multiplied with bk xk in the latter. Thus. + void prodp(float a[℄.rst onsider how the oeÆ ients of D relate to those of A. } + . int n){ // a. This gives us the program. k++) d[j+k℄ += a[j℄*b[k℄. for(int i=0. produ ing terms aj bk xj k . k<n. float d[℄. When A(x) and B (x) are multiplied. B . j++) for(int k=0. i++) d[i℄ = 0.b must have n elements. produ t d must have 2n-1. this will ontribute aj bk to dj k . float b[℄.

Clearly. the produ ts of terms aj xj and bi j xi j will produ e aj bi j xi and will thus ontribute. we require 0 j n 1 so that aj is well de. 190 Abhiram Ranade. Thus we will have: X di = aj bi j j The question is what should the limits on j be. 2011. Do not distribute We ould write this dierently by asking: whi h produ ts ontribute to the term dixi ? Clearly.

so that bi j is also well de.ned and 0 i j n 1.

n X max(0. float d[℄.k. produ t d must have 2n-1. float b[℄. we have expli itly written out numbers su h as 500.i-n+1).8 Array Length and onst values In the examples given above. i++){ d[i℄ = 0.j +k =i aj bk = min(i. int n){ // a. // Not allowed by the standard! This ode is not allowed by the C++ standard.i 1) aj bi j n+1) This an be easily oded as: void prodp(float a[℄.b must have n elements. in >> n. j<= min(i. Thus we an on lude that the limits are: di = X j. for(int i=0. } } 12. The C++ standard requires that the length be spe i. From the se ond we get i n + 1 j i. Arrays will often be used in programs for storing a olle tion of values. int a[n℄. and the total number of values in the olle tion will not be known to the programmer. i<2*n-1.ned. So you might onsider it more onvenient if we are allowed to write: int n.n-1). j++) d[i℄ += a[j℄*b[i-j℄. for(int j=max(0.1000 to spe ify the array length.

ed by an expression whose value is a ompile time onstant. A ompile time onstant is either an expli itly stated number. or it is an expression only involving variables whi h are de.

The pre.ned to be onst. e. onst int n = 1000.g.

arrays might be de. So using a onst name. and it an be used in all pla es that a variable an be used.x onst is used to say that n looks like a variable. but really its value annot be hanged.

// onvention to apitalize onstant names. onst int NMAX = 1000.ned as follows. int a[NMAX℄. . b[NMAX℄.

Do not distribute 191 So how do we use this in pra ti e? Suppose we want to de. Abhiram Ranade. 2011.

In this ase. de. the C++ standard will require us to guess the maximum number of students we are likely to ever have.ne an array whi h will store the marks of students.

in >> na tual. na tual.ne an array of that size. assert(NMAX <= na tual). So we might write: onst int NMAX = 1000. int a[NMAX℄. In the rest of the ode. and only use a part of it. b[NMAX℄. we remember that only the .

If this happens. the assert statement will ause the program to stop. and you will need to hange NMAX. and so write loops keeping this in mind. 12. In this ase we annot run the program.1 Why onst de larations? The above ode ould also dire tly de.rst na tual lo ations of a and b are used.8. re ompile and rerun. Note that it is possible that the user will type in a value for na tual that is larger than NMAX.

b[1000℄.ne int a[1000℄. instead of using the onst de.

we just need to hange the .nition. say we want arrays of size 2000 rather than 1000. However. If we had not used NMAX we would have to hange several o urren es of 1000 to 2000. the ode as given is preferable if we ever have to hange the required size. with the ode as given.

12.8.rst line to onst int NMAX = 2000.2 What we use in this book The GNU C++ ompiler that you invoke when you use the ommand s++ allows arbitrary expressions to be spe i.

the dis ussion above tells you how to hange it. It is worth thinking about how the index of an element gets used. this makes the ode mu h more ompa t and easier to understand at a glan e. So in the interest of avoiding lutter. The ode we give will work with s++. in the rest of the book. Sometimes the index at whi h an element is stored has no signi. If it does not work for some other ompiler. we will use arbitrary expressions while spe ifying lengths of arrays.ed as array lengths in de larations.9 Summary Arrays provide an easy way to store sets of obje ts of the same type. 12. As you an see.

This is a ommon idiom. We did this in the problem of printing roll numbers of students who had the highest marks. One way to do so is to s an through the array. Suppose we want to look for elements satisfying a ertain property. an e. Similar was the ase for the histogram problem. one element at a time. and he k if the element has the required property. as we did for the roll number in the marks display problem. we used the index to impli itly re ord the arrival order of the taxis. Or sometimes we an make a part of the data be the index. In the taxi dispat h problem. as in the ir le interse tion problem. .

Suppose the roll numbers in the lass do not go from 1 to the maximum number of students. Do not distribute 192 The idea of s anning through the array starting at index 0 and going on to the largest index is also useful when we want to perform the same operation on every element. Assume that for ea h student . and you will see it. for example. 12. or the program that the student belongs to. Write the marks display program for this ase. Finally. We used a somewhat ompli ated version of this in the ir le interse tion problem. in Exer ise 14. Abhiram Ranade.10 Exer ises 1. This is a very ommon idiom. For this we maintained two indi es: where the next element will be stored and whi h element will leave next. in the taxi dispat h problem we built a so alled queue so that the elements left the array in the same order that they arrived in. but are essentially arbitrary numbers (be ause perhaps they identify the year in whi h the student enters. and so on). e. but for ea h pair of ir les. where we wanted to perform a ertain a tion not for ea h ir le. 2011. print it.g.

and then the roll number. 2. when the roll numbers are arbitrary integers. i.rst the roll number is typed in.e. Suppose we want to . 3. Write the program to display who got the maximum marks for the ase above. Also assume that at the beginning the number of students is given.

between 0. but after all the numbers are given. our intervals are of width 0. Suppose in the previous problem you are asked to report whi h are the 10 highest values in the sequen e.e.e. a -1 is given. i. we want a ount of how many values are between 0 and 0. y oordinates of n points in the plane. 6. Write a program that provides the histogram for these ranges. and so on. using the operator ==.275. then 0. You are required to print the 10 largest numbers in the sequen e. Hint: use an array of length 10 to keep tra k of the numbers that are andidates for being the top 10.25 and 0. Suppose we are given the x. Write a program whi h determines this. be ause of the oating point format. When you al ulate slopes of line segments. Between 0 and 0.05. Make sure that you onsider every possible 3 points to test this. then 0. and so on. 4. We wish to know if any 3 of them are ollinear. our intervals are of width 0. So instead of asking whether two slopes are equal.25 and 0.05 and 0. 5. Write a program whi h does this. You are to write a program whi h takes as input a sequen e of positive integers. Finally.05. and that you test every triple only on e. there will be round-o errors.275 and 0.75 and 1. Say ea h value is a real number between 0 (in lusive) and 1 (ex lusive). Between 0.nd a histogram for whi h the width of the intervals for whi h we want the ounts are not uniform. i. You are not given the length of the sequen e before hand.1.025.3.75 our intervals are of width 0.25. you .05. and how frequently they appear. we want to know how many values are between 0. so you know the sequen e has terminated. The oordinates should be represented as floats.

or whether you should instead onsider the angle. the ar tangent of the slope. you should also ask yourself whether the slope is a good measure to he k ollinearity. Do not distribute should he k if they are approximately equal. 193 Abhiram Ranade. In fa t. i.e. This is a pre aution you need to take when omparing oating point numbers. i. whether their absolute dieren e is small. say 10 . 2011. Write a program whi h takes as input two ve tors (as de.e. 7.

ned in mathemati s/physi s) { represent them using arrays { and prints their dot produ t. Suppose you are given the number n of students in a lass. and their marks on two subje ts. 8. yi denote the marks in the two subje ts. Make this into a fun tion. Let xi . Then the orrelation is de. Your goal is to al ulate the orrelation.

A orrelation around 0 will indi ate in this ase (and often in general) that the two variables are independent. One way to redu e the randomness is to smooth the data by taking so alled moving averages. : : : . where yi is the average of xi k . xi k . Write a program whi h takes a sequen e whose length is given . what you want to know is whether there is any upward trend if you an somehow throw out the randomness. : : : . a 2k +1-window size moving average is a sequen e of numbers yk . you will see that the temperatures u tuate apparently errati ally from year to year. 9. Also plot the original sequen e and the moving average. Suppose you are given the maximum temperature registered in Mumbai on Mar h 21 of ea h year for the last 100 years. Write a program whi h takes a sequen e and the integer k as input. 10. A sequen e x . xn . as is generally believed. : : : . Given a sequen e of numbers x . and prints out the 2k +1 window-size moving average. You may use the dot produ t fun tion you wrote for the previous exer ise. : : : . You would like to know whether Mumbai has been getting warmer over the years. Note that a positive orrelation indi ates that x in reases with y (roughly) { whereas negative orrelation indi ates that x in reases roughly as y de reases. If you merely plot the data.ned as: 5 p P n P P P xi yi xi yi p P P ( xi )2 n yi2 (P yi) Write a program that al ulates this. The weather is expe ted to behave somewhat randomly. xn (note that the length is n + 1) is said to be a palindrome if xi = xn i for all i. You would like to know from your data whether this might be a reasonable on lusion. yn k.

We . The Eratosthenes' Sieve for determining whether a number n is prime is as follows.rst and says whether the sequen e is a palindrome. 11.

: : : . n on paper (or a lay tablet if we an get it!). We then start with the .rst write down the numbers 2.

then it must be a prime. and ross out all its proper multiples.rst un rossed number. Earlier in the ourse we had a primality testing algorithm whi h he ked whether some number between 2 and n 1 divided n. Write a program based on this idea. Then we look for the next un rossed number and ross out all its proper multiples and so on. Is the new method better than the old one? n x2i 2 1 +1 0 + . If n is not rossed out in this pro ess.

but keep the array sorted as you read. after you read the . You are required to sort them. Suppose we are given an array marks where marks[i℄ gives the marks of student with roll number i. In other words. move the roll number along with the marks. along with the roll number of the student who obtained the marks. We are required to print out the marks in non-in reasing order. Suppose you are given a sequen e of numbers. Do not distribute 12. 13. Modify the sorting algorithm developed in the hapter to do this. 194 Abhiram Ranade. As you ex hange marks during the ourse of the sele tion sort algorithm. pre eded by the length of the sequen e. In this exer ise you will do this using the so alled Insertion sort algorithm. Hint: Use an additional array rollNo su h that rollNo[i℄ equals i initially. The idea of the algorithm is to read the numbers into an array. 2011.

you must make sure that they appear in the .rst i numbers.

rst i elements of the array in sorted (say non-in reasing) order. So when you read the i +1th number. you must .

B of lengths m. then you should move the numbers in positions j + 1 through i 1 (note that the indi es or positions start at 0) forward in the array by 1 step.n. Write the program that does this. Suppose you dis over that it needs to be pla ed between the numbers that are urrently at the j th and j + 1th position.nd where it should be inserted. 14. Then the newly read number an be pla ed in the j + 1th position. You are supposed to . Suppose you are given two arrays A. Suppose further that the arrays are sorted in non-de reasing order.

elements must move out of A and B into C.2.e.B. keeping it aside.6.3.7.2.5 and B ontains 2. and then moving a ard from the top to the bottom without showing it to you.3. elements always move out from the front of A. Hint: Clearly. He then takes the next ard and puts it at the bottom of the de k without showing it to you. Then he shows you the ard now at the top of the de k. He repeats the pro ess: showing you the top ard. then C should ontain 1.4. A friend (\the magi ian") shows you a de k of ards. i. and move into the ba k of C? 15. It turns out (magi ally!) that you see the ards in in reasing fa e value.ll an array C of length m+n so that it ontains pre isely the same numbers whi h are present in A.3. whi h turns out to be the 2. turns it fa e up. Can you argue that for the purpose of this movement all arrays behave like queues.e. the . He puts the ard away.5. He pi ks up the top ard.4. In other words. and it is seen to be the a e.6.7.3. but they must appear in non-de reasing order in C. if A ontains the sequen e 1. i.B.2.

Write a program that explains the magi . Of ourse. then the 3. . then the 2.rst ard to be exposed is the a e. then the 4. i.e. the \magi " is all in the order in whi h the ards were pla ed in the de k at the beginning. and so on until the King.

Q(x) returns their omposition R(x) = P (Q(x)). 17. you are given its length Li and a maximum speed si with whi h trains an run on it. Write a fun tion whi h given polynomials P (x). 18. For ea h ith segment. Write the binary sear h ode without re ursion.gures out this order? Hint: Reverse the pro ess. Consider a railway tra k onsisting of some n segments. The 2 2 2 2 2 . Say P (x) = x + 3x + 5 and Q(x) = 3x + 5x + 9. 16. Then R(x) = (3x + 5x + 9) + 3(3x + 5x + 9) + 5.

How qui kly an the train omplete this journey? Make sure your ode works for all possible values of the parameters. and it depends upon the quality of rails used. Suppose the train starts at rest at one end of the tra k and must ome to rest at the other end. for simpli ity). 2011. . the maximum de eleration d (again independent of the speed) it is apable of. You are also given the data for a ertain lo omotive: its maximum speed s and the maximum a ereration a it is apable of (assume this is independent of the speed. whether the tra k has turns. Do not distribute 195 maximum speed for dierent segments an be dierent. Abhiram Ranade. and other fa tors.

how it is built is des ribed in Chapter ??. as we will study later. It turns out that the standard. An ordinary (one dimensional) array an be thought of as a sequen e of values. More often. we rarely work with single hara ters. However. In hapter 3 we dis ussed the har datatype for storing hara ters. we dis uss multidimensional arrays. or strings/sequen es of hara ters. A two dimensional array an be thought of as a table (rows and olumns) of values. C++ allows us to build our own. in luding that of . Next. This is not quite re ommended in C++. we will need to manipulate full words.Chapter 13 More on arrays We begin by onsidering the problem of representing textual data. We present one su h me hanism whi h is a part of simple pp. However. more onvenient me hanism. In this hapter we only dis uss how to use this me hanism. But it is worth knowing this representation be ause the C++ re ommended representation builds upon this. built-in way of representing multidimensional arrays in C++ is somewhat in onvenient. A hara ter string is ustomarily represented in C as an array of hara ters. We dis uss a number of appli ations of two dimensional arrays.

nding shortest paths on a map. 13.1 Chara ter strings An array of hara ters an be de.

ned just as you de.

har name[20℄.ne arrays of floats or ints. residen e[50℄. The above de.

ostensibly for storing the name and the residen e. Sin e we will usually not know the exa t number of hara ters in a name or in an address. name and residen e of lengths 20 and 50. it is ustomary to de.nes two arrays.

we learly do not want the name[7℄ through name[19℄ printed.ne arrays of what we guess might be the largest possible length. is that instead of storing the length expli itly. The onvention used in the C language. The string is 7 hara ters long. we will be storing 'S' in name[0℄. we store 196 . While printing the string for example. and we will see better alternatives in later hapters. and inherited into C++ from there. and it is. So if we want to store a hara ter string \Shivaji" in the array. and you would think that we should store this length somewhere. 'h' in name[1℄ and so on. This might seem wasteful.

Spe ial onstru ts are provided for initializing hara ter arrays. and this an be written as 'n0'. Raigad". har residen e[50℄ = "Main Pala e. So it unambiguously marks the end of the string. The hara ter string \Shivaji" has 7 hara ters. So these will be pla ed in the . and is not expe ted to be a part of any real text string. The spe ial hara ter used is the one with ASCII value 0. Do not distribute 197 a spe ial hara ter at the end of the a tual string. Abhiram Ranade. So indeed we may write har name[20℄ = "Shivaji". Note that 'n0' is not printable. 2011.

rst 7 elements of name. We an manipulate strings stored in har arrays by going over the elements in a for loop. Note by the way that apital and small letters have dierent odes.1. would ause the ontents of name from the beginning to the 'n0' hara ter to be printed on the s reen. . Here is an alternative form. The eighth element. Following the previous dis ussion. until a 'n0' hara ter is en ountered. Thus hara ter arrays passed to fun tions an be printed in the expe ted manner.1 Output Printing out the ontents of a hara ter array is simple. where harptr is an expression whi h evaluates to a pointer to a har type. 13. Similarly only 20 elements of residen e will be initialized. 13. for example. in luding the last 'n0'. This statement auses hara ters starting from the address harptr to be printed. The general form of the above statement is: out << harptr. Assuming name is a hara ter array as before. If name is a hara ter array. out << name. In this. C++ will al ulate the lengths of name and residen e. har name[℄ = "Shivaji". har residen e[℄ = "Main Pala e. name[7℄ will be set to 'n0'. these will be set to 8 and 20 respe tively. Raigad".1. It is the responsibility of the programmer to ensure that the array being printed indeed ontains a 'n0' hara ter.2 Input To read in a string into a har array you may use the analogous form: in >> harptr. then name indeed is of type pointer to har.

whi h we explain with an example. Two points are worth noting: 1. The statement will ause a whitespa e delimited string typed by the user to be read into the memory starting at the address denoted by harptr. har name[20℄. The hara ter string starting with the . out << "Please type your name: ". After storing the string the string the 'n0' hara ter will be stored. 2011. in >> name. the initial whitespa e hara ters will be ignored. The se ond statement asks you to type your name and the third. There are a ouple of points to be noted. Consider the following ode. an expression of type pointer to har. Abhiram Ranade. Do not distribute 198 Here harptr ould be the name of a har array. in >> name. or more generally. reads in what you type into the array name. From what you type.

So for example we an write: . following "Abhiram" a null hara ter. As you may guess. This statement is potentially unsafe. The newline hara ter is not opied.e. in luding whitespa e hara ters.getline(x. and name[7℄ would be set to 'n0'.rst non-whitespa e hara ter and ending just before the following whitespa e hara ter will be taken and pla ed in name. Thus the letters 'A' through 'm' would go into name[0℄ through name[6℄. where x must be a name of a har array (or more generally a pointer to har). In other words. Thus if I type Abhiram Ranade with some leading whitespa e. if the user types more hara ters than the length of name. until one of the following o urs A newline hara ter is typed by the user. If a user types in more hara ters than the length of the array. Note that all this is very onvenient in that the a single statement reads in all the hara ters. this is an error of ex eeding the size of the array. Next. In this ase all hara ters upto the newline are opied into x. i. followed by a 'n0' hara ter. n-1 hara ters are typed without a newline. This will ause whatever the user types. to be pla ed into the array x. It is dis arded. the leading whitespa e will be dropped and only "Abhiram" would go into name. In other words. with no whitespa e hara ters in between them. it is ustomary to use the length of x as the argument n. 2. In this ase all the hara ters are pla ed into x. The safe alternative to this is to use the following ommand. and further the 'n0' is also automati ally pla ed after the last hara ter read in. and n an integer. then the hara ters typed in will be written to the area of memory starting with name[0℄. possibly damaging the memory following the array name. in. all those will also be stored.n). 'n0' would be stored.

and we will have no danger of over owing past the array limit.getline(name. In this ase at most 19 hara ters that the user types will be opied. Interestingly enough. the value of a string onstant is not the text.1. The ompiler stores the string somewhere in memory (followed by 'n0'). and you may refer to it. but a pointer to the . su h as "Please type your name:" onstitutes a string onstant in C++. in. Abhiram Ranade.20). 2011. 13. Do not distribute 199 har name[20℄.3 Chara ter string onstant Quoted text.

1. and in that they ontain a 'n0' hara ter whi h marks the end of the useful portion of the array.1. Thus when you write out << "Please type your name:".1. So pro essing them is reasonably straight forward. Note that hara ters are a subtype of integers. just as we do for integers. you are merely using the general form mentioned in Se tion 13.rst hara ter of the text.4 Examples Chara ter arrays behave like ordinary integer arrays. 13. ex ept when it omes to reading and printing. and ompare them. Our . and as su h we an perform arithmeti on hara ters.

e. The fun tion does not worry at all about the lengths of the 2 arrays as de.rst example is a fun tion for opying a string stored in an array sour e to another array destination. i. ex ept that we must only worry about the useful portion of the sour e array. This is like opying other arrays. till the o urren e of the 'n0' hara ter.

it is assumed that the all has been made ensuring that indi es will not ex eed the array bounds. void str py( har destination[℄. i.ned. destination must be long // enough to hold the entire string + '\0'. destination[i℄=sour e[i℄. would appear . har sour e[℄) // pre ondition: '\0' must o ur in sour e. // opy the '\0' itself } As an example of using this."Einstein") whi h would simply set the name to \Einstein". sour e[i℄ != '\0'. Thus we an write str py(name. { int i. note that a string onstant an be used any pla e a pointer to har is needed. Here is a more interesting fun tion: it takes two strings and returns whi h one is lexi ographi ally smaller. i++) destination[i℄=sour e[i℄.e. for(i=0.

starting at the 0th. The fun tion simply ompares orresponding hara ters of the two strings.rst in the di tionary. If the end of the strings is rea hed without .

. then it means that the two strings are identi al.nding unequal hara ters.

Do not distribute 200 in whi h ase we must return '='. If at some omparison we . Abhiram Ranade. 2011.

then the string that ends is smaller.nd the hara ter in one string to be smaller than the other. So if we . while the pre eding hara ters are the same. This logi is implemented in the ode below. that string is de lared smaller. If one string ends earlier. We maintain the loop invariant: at the beginning of the loop hara ters 0 through i-1 of both arrays must be non null and identi al.

If a[i℄ is null but not b[i℄.nd both a[i℄ and b[i℄ to be null. learly the strings are identi al and hen e we return 0. then a is a pre.

Be ause pre.x of b.

If none of these onditions apply. If a[i℄>b[i℄ we return '>'. We pro eed similarly if b[i℄ is null but not a[i℄. we return '<'. then the ith hara ter in both strings must be non-null and identi al.xes appear before longer strings in the di tionary. So the invariant for the next iteration is satis. if a[i℄<b[i℄ we return '<'.

So we in rement i and go to the next iteration.i-1℄ if(a[i℄ == '\0' && b[i℄ == '\0') return '='.ed. Say you typed: Mathemati s Biology then it would print out > and stop. while(true){ // Invariant: a[0.40). } } This may be alled using the following main program.. in. har b[℄) // returns '<' if a is smaller. { int i = 0. be ause \Mathemati s" appears after \Biology" in the di tionary order. main(){ har a[40℄. if(a[i℄ == '\0') return '<'. it would expe t you to type two lines. } If you exe ute this program. out << a << " " << ompare(a. '>' if b is smaller. i++.getline(a..i-1℄ == b[0. har ompare( har a[℄. if(a[i℄>b[i℄) return '>'. 13. '=' if equal. we have exe uted C++ programs by spe ifying the name of the exe utable . b[40℄. if(a[i℄<b[i℄) return '<'.b) << " " << b << endl. in.40).getline(b. if(b[i℄ == '\0') return '>'.2 Command line arguments to main So far.

on the ommand line.out.le. Spe i. usually a.

the program is exe uted by typing: . ally.

you may write: a. C++ does allow you to provide arguments on this line itself. whi h an be pro essed by your program.out or ./a.out Mathemati s Biology and want the program to take the . 2011. Do not distribute 201 a.out on the shell ommand line. For example. Abhiram Ranade.

} In this we have used the stringstream fun tionality provided in C++. the elements are extra ted from the supplied argument string s. #in lude <sstream> int main(int arg . and a se ond argument argv of type pointer to pointer to har. stringstream(argv[1℄) >> x. rather than any . You an also pro ess numeri al ommand line arguments quite easily. This an be done using an alternative (overloaded) de laration provided for main. Thus main may take an integer argument arg . Thus for a. and ompare them lexi ographi ally. then in your program arg gives the number of words typed on the ommand line. har** argv){ out << argv[1℄ << ompare(argv[1℄. har** argv). argv is an array of pointers to har. Suppose you wish to write a program that takes two oating point numbers as ommand line arguments and prints their produ t. Here is how it an be written. But this time. The argument argv is an array of arg elements. int main(int arg .y.rst and se ond word on the ommand line. Now we an use the >> operator to extra t elements. If you use this form of main.out Mathemati s Biology the value of arg would be 3. and onverts it to an output stream (su h as out). The fun tion stringstream takes a single argument s whi h is a hara ter string. Thus our main program to ompare ommand line arguments lexi ographi ally would be as follows. of ourse. } This has to be ompiled in luding the fun tion ompare. har** argv){ double x. in luding the name of the exe utable program (a.out or other). out << x*y << endl. stringstream(argv[2℄) >> y. argv[2℄) << argv[2℄ << endl. by in luding <sstream>. In other words. with the ith element argv[i℄ being the address of the ith ommand line word (typi ally alled ith ommand line argument). int main(int arg .

Similarly a double value would be extra ted into y from the third word. 20000 would indeed be printed. Thus if you typed a. .out 4 5e3 The answer. would extra t a double value from the se ond word typed on the ommand line.le or the keyboard. Thus stringstream(argv[1℄) >> x.

2011. For su h ases. we will run into obje ts like matri es whi h are olle tions of elements des ribed using two indi es. Do not distribute 202 13.3 Two dimensional Arrays Sequen es of numbers are naturally represented as arrays. C++ provides 2 dimensional arrays. However. Abhiram Ranade. Here is an example of how a two dimensional array might be de.

. a[1℄[0℄. i. // But s++ will allow integer expressions. . and 0 j < n. a[m-1℄[n-1℄. in the order a[0℄[0℄.e..ned: float a[m℄[n℄.n are said to be the . . a[1℄[n-1℄. These variables are a essed as a[i℄[j℄ where we require 0 i < m..n must be ompile time onstants as per C++ standard. // m. The variables are stored in the so alled row major order in memory. . This auses spa e for m*n oating point variables to be allo ated.. a[0℄[1℄.. a[0℄[n-1℄.. The numbers m.

The ode below. starts indi es at 0. and B an n p matrix. The ode also shows how a two dimensional array an be initialized in the de. We will also refer to them as the number of rows and the number of olumns respe tively. then there produ t is an m p matrix C where n X ij = aik bkj k =1 where we have let the array indi es start at 1. Remember that if A is an m n matrix.rst and se ond dimension of the array. Here is a program fragment that reads in two matri es and prints their produ t. of ourse. Manipulating 2 dimensional arrays is similar to 1 dimensional { we will just have 2 loops over the two indi es rather than just one. as is ustomary in Mathemati s.

for(int k=0. } We may de. float a[3℄[2℄={{1. b[2℄[4℄={{1.8}}. i<3.6. out << endl. j<4. The values for ea h row must appear in bra es.6}}. j++){ [i℄[j℄ = 0. for(int i=0.4}. and these in turn in an outer pair of bra es. j<4.3. i++){ for(int j=0.{5.2.{3. k++) [i℄[j℄ += a[i℄[k℄*b[k℄[j℄.{5. i<3. k<2. i++) for(int j=0. j++) out << [i℄[j℄ << " ".2}. } for(int i=0.nition itself if you wish.7. [3℄[4℄.4}.

For example we ould write: har ountries[6℄[20℄ = {"India". with initialization. ."Nepal"."China".ne two dimensional arrays of hars. "Bangladesh"."Sri Lanka". whi h is of ourse optional."Pakistan"}.

2011. Abhiram Ranade. Do not distribute 203 Here the .

ountries[1℄). So if we write ompare( ountries[0℄. where ompare is as de. the address of the ith string. Thus ountries[i℄ will return the address of the zeroth hara ter of the ith string stored in the array. Applying only one index to the name of a two dimensional array returns the address of the zeroth element of the orresponding row. and so on for the six strings. this is the way to refer to one of the strings stored.rst string. in other words. "India" is deemed to initialize the zeroth row. For hara ter arrays.

we know that i must be stri tly less than 6 if the ountry was found in ountries. However."Nepal"."China". in the alled fun tion."Colombi". and equal to 6 if not found. It takes as input a string from the keyboard. i++){ if( ompare( ountry. ountries whi h lists ountries.1 Passing 2 dimensional arrays to fun tions It is possible to pass a two dimensional array to a fun tion. in. It prints out the name of the orresponding apital if the string is in the list of ountries stored in ountries.3. Hen e we print the message that we dont know the apital only if i is 6 at the end. This he k is made using our ompare fun tion. har ountry[wordLength℄. and apitals whi h lists orresponding apitals. for(i=0. ountries[i℄) == '='){ out << apitals[i℄ << endl.getline( ountry. Thus we might write: void print( har ountries[℄[20℄."Beijing". 13. Note that the fun tion must return '=' if the two arguments are identi al strings."Pakistan"}. } } if(i == 6) out << "Dont know the apital. it would return '<' as the result be ause India will pre ede Sri Lanka in the di tionary order. i<6. int noOfCountries){ .4. break."Islamabad"}.1.wordLength) } int i. the se ond dimension of the array parameter must be given as a ompile time onstant.ned in Se tion 13. When the loop terminates."Sri Lanka".\n". out << "Country: ". Here is a program whi h has two arrays."Kathmandu". main(){ onst int wordLength = 20 har ountries[6℄[wordLength℄ = {"India". har apitals[6℄[wordLength℄ = {"New Delhi". "Bangladesh". "Dhaka".

This may be alled as print( ountries. Abhiram Ranade. i<noOfCountries. where the se ond argument is the . Do not distribute } 204 for(int i=0. 2011.6). i++) out << ountries[i℄ << endl.

It will print out the ountries on separate lines. This an be passed to fun tions. So in the next se tion we will see a two dimensional array that has been provided as a part of simple pp. this makes it impossible to write a general matrix multipli ation fun tion for matri es of arbitrary sizes. and the fun tions an be written without having to know at ompile time either the .rst dimension of the ountries array. This is not too useful. For example. be ause any su h fun tion an only be used for arrays in whi h the se ond dimension is 20.

13. where ea h row gives the x.2 Drawing polygons in simple pp simple pp ontains the following fun tion for drawing polygons: Polygon pName( x.Verti es. The parameter olour must be spe i. and Verti es is a two dimensional float array with n rows and 2 olumns.3.y oordinates of the verti es.fill). This will reate a polygon named pName. then the standard two dimensional arrays are useful. The parameters x. y.rst or the se ond dimension of the array! But if we do know the se ond dimension. The parameter n is an integer giving the number of verti es. y). y give the rotation enter of the polygon. Here is how they an be used in drawing polygons in simple pp graphi s.n. olour. relative to the enter ( x.

and fill is a boolean denoting whether the olour must .ed as COLOR("red") for example.

pentaV. float pentaV[5℄[2℄.COLOR("red"). We reate a regular pentagon and a pentagonal star. Then we rotate them. starV[i℄[0℄ = 100 * os(4*PI/5*i).5.200.starV. starV[i℄[1℄ = 100 * sin(4*PI/5*i). Note that the boundary may interse t itself. i++){ . i<5. so we may use all the ommands for sprites (Se tion 4) on polygons.5. main_program{ initCanvas("Pentagon").ll the polygon or merely be the olour of the boundary. A polygon is a sprite.true). Polygon star(200. for(int i=0. then going to vertex 1 and so on till vertex n-1. The boundary of the polygon is tra ed starting at vertex 0.true).COLOR("blue"). i++){ pentaV[i℄[0℄ = 100 * os(2*PI/5*i). Here is an example. } Polygon penta(200.400. i<100. pentaV[i℄[1℄ = 100 * sin(2*PI/5*i). for(int i=0. starV[5℄[2℄.

right(5). Cal ulating the oordinates of the \inner" verti es is a bit messy. though. This will essentially give you a 2 dimensional array of floats. Note that there is a more natural ways of spe ifying the star shape: onsider it to be a ( on ave) polygon of 10 verti es. Thus we ould have given the oordinates of the 10 verti es in order.1). The array is named ab . and this an be any identi.left(5). Do not distribute } } 205 penta. 2011.5). 13. star. for example: matrix<float> ab (3. Abhiram Ranade. wait(0. getCli k(). You may write.4 A home-made 2 dimensional array In simple pp we have provided an alternate me hanism to represent two dimensional data.

es as usual. The dimensions of the array are 3. and these are spe i. 5.

In what follows. we will write matrix to mean matrix<T> for all possible types T. and ab . The name ab has type matrix<float>. separated by a omma. You an get the number of rows and olumns in a matrix su h as ab by writing respe tively ab . There are several dieren es between standard C++ two dimensional arrays and this new 2 dimensional array. ab (i.5 for the de.j) will refer to the element in row i and olumn j. Indexing is also to be done using a similar notation. 1.ed not in two pairs of square bra kets. e.g.rows(). olumns(). Note that by using other types instead of float inside the angled bra kets <> following matrix you an get 2 dimensional arrays of other types too. but in a single pair of parentheses. These would respe tively evaluate to 3.

and hen e it would be good to avoid opying. 2. and nothing else is needed. then it should be marked a referen e parameter. i. So it is a good idea to pass all matri es by referen e.rows() and pqr. Usually matri es will be large. The name must be passed.nition of ab as above.e. 3. then we an get the rows and olumns in the passed matrix by writing pqr. Those matri es that will not be modi. a new opy is made for the alled fun tion. Thus if you want to modify a parameter. If the name of the orresponding parameter is pqr. A matrix an be onveniently passed to fun tions. Data of type matrix is passed by value. olumns().

write ab (i.j) it is . 4.e. Whenever you a ess an element i.ed by the fun tion should be marked onst.

If the indi es are in the range. . then a message is printed. and the indi es that were a tually used.rst he ked whether the indi es i.j are in the required range. giving the allowed range. then you get a ess as usual. If they are not.

Do not distribute 206 5. A matrix obje t annot be initialized as a part of the de. 2011. Abhiram Ranade.

i++) for(int j=0. in >> b. in >> a.a. . void matmult(matrix<float> & . whi h will ause array elements to be read from the keyboard in row major order. the body is essentially the same as in Se tion 13. whi h will ause the array to be printed in the row major order. } } We want the result ba k in . // number of olumns in a = number of rows in b // number of olumns in b = number of olumns in // // should be different from a. k<a. matrix<float>& a.rows().k)*b(k. The other parameters are onst referen e As you an see. 6.nition. You an write out << ab . You have to expli itly write assignment statements to do so. olumns().1 Matrix multipli ation fun tion Suppose we wish to multiply matri es represented by arrays a.j). we get the starting address of the orresponding row. matrix<float> & b) // pre ondition: number of rows in = number of rows in a. i< . In standard two dimensional arrays. ex ept that we have pi ked up the loop bounds from the rows/ olumns of the argument matri es.1). j< . (2.b and produ e a matrix . matmult( . if we supply only one index. You an write in >> ab . main(){ matrix<float> a(2. } out << .j) = 0. Here is the fun tion for doing it. We an indeed write ab (i) to get the starting address of the ith row. j++){ (i.1). so that is a referen e parameter. 13. This feature ontinues to hold.j) += a(i. 7. A possible main program is as follows. { for(int i=0. for(int k=0. one row per line. We give examples whi h illustrate these features.4. b(3. k++) (i.3.b).3). olumns().b.

// names(0) = address where 0th string starts. str py(names(1)."Anita"). out << names(0)<< endl. 207 Abhiram Ranade. and indeed we an use the str py fun tion de.20). Do not distribute We onsider one more example. str py(names(0).1)='m'."Raju"). out << names(1)<< endl. main(){ matrix< har> names(2. } names(0. The expression names(0) gives the address where the zeroth string an begin. out << names(0)<< endl. 2011.

the ve tor of unknowns by x and the right hand side ve tor by b.ned in Se tion 13. Similarly we store into names(1). The last two lines show the ee t of hanging one element. The dire t way to solve a system of equations is by a pro ess alled Gaussian elimination . we have the matrix equation Ax = b in whi h we are to solve for x given A. Say we are given simultaneous equations: 3x + 5x = 10 2x + 6x + 8x = 38 7x + 4x + 9x = 22 Then they an be onveniently represented by the matrix equation 2 0 3 5 3 2 x 3 2 10 3 4 2 6 8 5 4 x 5 = 4 38 5 7 4 9 x 22 Denoting the matrix by A. Observe .4 to store data into it. in fa t a form of it alled Gauss-Jordan elimination. b.1.5 Linear simultaneous equations One of the most important uses of matri es and two dimensional arrays is to represent linear simultaneous equations. You should see \Amita" get printed rather than \Anita". 13.

aii = 1 and aij = 0 for all i.e. Thus for this b is itself the solution. Multiplying out we would get x = b. j 6= i.rst that if the matrix A was the identity matrix. i. We will make modi. then the problem is very easy. This suggests a strategy.

ations to A. b su h that the modi.

ations do not hange the solution of Ax = b. . If at the end of the sequen e 2 3 1 2 3 1 2 3 1 2 3 1 1 The method is a tually mu h older than Gauss.

Do not distribute of modi. 208 Abhiram Ranade. 2011.

ations. say we add the . b) indeed do not hange the solutions to the system. and repla e the latter equation by the result. Another operation is to add one equation to another. In our example. This is akin to multiplying a row of the matrix A and the orresponding element of the ve tor b by a (the same) onstant. It turns out that several operations performed on the system of equations (and hen e A. One su h operation is to multiply any equation by a onstant. our matrix A be omes the identity matrix then the value of b at that time would itself be the solution.

Thus we get the equation 2x + 9x + 13x = 48. We repla e the se ond equation with this equation.rst equation to the se ond. This is su in tly done in the matrix representation: we merely add the .

and the .rst row of A to the se ond row.

while the other elements remained the same. Thus the se ond row of A would then be ome [2 9 13℄ and the se ond element of b would be ome 48.rst element of b to the se ond element of b. without hanging the solution. b. so that the . We now show how we an hange A.

0 (read top to bottom).0.rst olumn of A be omes 1. identi al to the .e. i.

rst olumn of the identity matrix. 1. The same pro ess an then be adapted for the other olumns. If the oeÆ ient of x is zero in the .

Then ex hange equation 1 and equation i. This orresponds to ex hanging row 1 and row i of A and also element 1 and element i of b. Doing this for our example we get: 2 2 6 8 3 2 x 3 2 38 3 4 0 3 5 5 4 x 5 = 4 10 5 7 4 9 x 22 1 2 3 1 1 1 1 2 3 2. Suppose the ith equation has a non-zero oeÆ ient for x . Divide the . pi k any equation whi h has a non zero oeÆ ient for x .rst equation.

We thus get 2 1 3 4 3 2 x 3 2 19 3 4 0 3 5 5 4 x 5 = 4 10 5 7 4 9 x 22 11 1 2 3 3.rst equation by the oeÆ ient of a . add ai times the . For ea h i.

Say we do this for row 2. Thus we must add a = 0 times the .rst equation to equation i.

we add -7 times the . So nothing need be done. So we then onsider row 3.rst row. Sin e a = 7.

rst equation to equation 3. Thus we now have: 2 1 3 4 3 2 x 3 2 19 3 4 0 3 5 5 4 x 5 = 4 10 5 0 17 19 x 111 It should be lear that the above pro ess would indeed make the .

rst olumn identi al to the .

In a similar manner.rst olumn of the identity matrix. The . you should be able to get the other olumns to mat h the identity matrix.

Suppose you have managed to make the .rst step in the above des ription deserves more explanation.

rst j 1 olumns of A resemble the .

rst j 1 olumns of the identity matrix. Now the .

rst step above instru ts you to .

nd an equation in whi h the oeÆ ient of xj is non-zero. For this. you should only look at equations j through n. and not onsider the .

It will not su eed if akj = 0 1 21 31 1 2 3 .rst j 1 equations. This step may or may not su eed.

1. The ode for doing all this is left as an exer ise. In this ase. // The solution to Ax=b will be omputed and returned in x if it is unique. // If the solution is not unique. Our goal is to take this information. as in Figure 13. then x will not be altered. In this ase you should report failure. float b[℄. You are expe ted to write a fun tion whi h does this. Sometimes we do not need the shortest path length from every town (\all sour e") to every other town. 2011. and // false will be returned. and print out the length of the shortest path between every pair of towns. 13. float x[℄). and b. but only from a spe i. // If the solution is unique. // A must be an n x n matrix. As you an see there are points representing towns and lines onne ting them representing roads. having the following prototype bool solveLS(matrix<float> & A. it may have many solutions or no solutions at all.6 All sour e shortest paths Suppose we have a road network. Next to ea h road is given the length of the road in km. Do not distribute 209 for all k = j : : : n. it turns out that the system of equations does not have a unique solution. Abhiram Ranade. true will be returned as the result. x must be n element ve tors.

with the length of the road being the weight of the orresponding edge. The . In these terms. Graphs in whi h edges have numbers asso iated with them are said to be weighted. the numbers represent the length of the roads. In our problem.4. our graph is weighted.2 the road network is a graph in whi h towns are verti es and roads are edges. and so we will all them edge lengths rather than edge weights. with the number alled the weight. town to other towns. We will onsider su h \single sour e" problems in Se tion 21. Note that in our terminology of Se tion 10.

The only entries of D we have not de. you may assume for simpli ity that dij = dij . If there are n towns/verti es. We will shortly see how to represent 1 in C++. of ourse. say D. This is relevant in our ase: the distan e in one dire tion an be dierent than the other. However. the length (or weight) of the edge from i to j . and hen e equivalent to no road. It needs some intuition to de ide what to store in dij if there is no road from town i to j 6= i. We will all this the dire t onne tion matrix. The intuition behind this is: a road of length 1 an be onsidered useless for travelling. whi h we will all G. The orre t number to store turns out to be 1. is how to represent our graph. These numbers must be given to us as part of the input. we will use an n n matrix. espe ially in hilly areas. Note that this leaves open the possibility of storing dierent values in dij and dji. be ause it will store information about dire t road onne tions. A matrix turns out to be rather onvenient for this. In general. whi h in our ase is the length of the road from town i to town j is stored in dij .rst question.

dii. The intuition here is that the dire t distan e from a town to itself should be onsidered 0. So indeed you may write: .ned so far are the diagonal entries. There is a spe ial bit pattern for representing 1 in the IEEE oating point standard (Appendix E) whi h C++ implements. and the name given to the bit pattern is HUGE VAL. We set all dii = 0. It turns out that in C++ you an indeed represent 1.

The onvenien e of this notation is that HUGE VAL behaves like in. 2011.1: S hemati Map float distan e = HUGE_VAL. Do not distribute Nagpur 500 Nashik 200 Mumbai 220 160 50 Pune 450 Satara 300 Kolhapur Figure 13. 210 Abhiram Ranade.

nity! If you multiply a number and in.

nity you expe t to get in.

nity. If you . and indeed this happens.

nd the minimum of some number and in.

Or if you divide any .nity you expe t to get that number.

nite number by in.

nity. you expe t that the result will be zero. All su h expe tations are satis.

4=Kolhapur. our matrix would be (with 1=Mumbai.6. 3=Nashik.ed! Without you doing anything spe ial! For the data in our map.1 Algorithm Let us . 5=Nagpur. 2=Pune. 6=Satara): 2 0 160 200 450 1 1 3 6 160 0 220 1 1 50 7 7 6 7 6 200 220 0 1 500 1 7 D=6 7 6 450 1 1 0 1 300 7 6 4 1 1 500 1 0 1 5 1 50 1 300 1 0 13.

rst de.

Q are m n and n p matri es respe tively. Suppose P. Then R = P Q is de.ne an unusual matrix multipli ation.

ned as the m p matrix in whi h entry rij = min(pi + q j . pi + q j . pin + qnj ). : : : . and addition instead of multipli ation. ex ept that we perform the min operation instead of addition. 1 1 2 2 . Noti e that this is same as ordinary matrix multipli ation.

3. the interpretation is that there is no path at all that goes from i to j . We simply square D repeatedly. Note that xij might turn out to be 1. It requires us to ompute X = Dn . However. In this ase. 211 Abhiram Ranade.6. spe i. 2011. You might think that to ompute Dn we will need to perform n 2 matrix multipli ations. Then xij gives the length of the shortest path from i to j . where matrix multipli ation is performed using the operator . Why this is so will be explained in Se tion 13. this is not true. Do not distribute Our algorithm for al ulating shortest paths is extremely simple.

Note that using the algorithm above. ally we use the following algorithm. we have al ulated Dn0 using dlog (n 1)e matrix multipli ations. after two we will have X 0= D . For t = 1 to p = dlog (n 1)e do Compute X = X X . X = D 2. then X = D and so on. After one iteration of the above algorithm we will have X = D . 3. 1 1 2 2 4 8 2p 2 1 2 13. mu h less than the obvious n 2. and after p = dlog (n 1)e we will have X = D = Dn where n0 = 2p is the smallest power of 2 no smaller than n 1.2 Exe ution example Let us exe ute one iteration of the above algorithm for our matrix D as de.6. return X . end for 4. 1. We will see shortly n0 that D = Dn .

if you work it out you will see that x = 210. going through Pune and Satara). On the other hand. Thus there is some progress as we go to D from D. x and d are both 1. there was not dire t onne tion. 2. In our matrix D. d + d . Indeed. d + d . 220 + 1. : : : . i. whi h is indeed the shortest path length between Mumbai and Satara. we will have all orre t lengths. 0 + 1. though not perfe tly. d + d . On the other hand. Thus we will ompute X = D = D D. 2 34 31 14 32 24 33 34 34 44 35 54 36 64 2 34 16 54 2 54 . So as we go to D . when we are done omputing n0 D . ng Thus the entry xij for i = 3 (Nashik) and j = 4 (Kolhapur) will be x = minfd + d . our estimate has improved onsiderably. however it is a good estimate of the a tual shortest path length (570. d + d . 1 + 0. 1 + 300g = 650 Note that 650 is not the length of the shortest path from Nashik to Kolhapur. and so there is no progress on this. d + d g = minf200 + 450. we had d = 1.e. from 1 to 650. 500 + 1. as we will argue next. Thus we will have xij = minfdik + dkj j k = 1.ned earlier.

3 Explanation of the algorithm For the ease of dis ussion it is onvenient to onsider two additional kinds of edges into our graph.6. 212 Abhiram Ranade. 2011. The . Do not distribute 13.

with su h edges. Further. We asso iate the length dii whi h we already set to 0. we will onsider a ghost edge from vertex i to vertex j 6= i if no real edge exists. In the . A ghost edge will be asso iated with the length dij whi h we already set to 1 earlier.rst are the so alled self-loop edges going from every vertex i to itself.

self-loop and ghost. i. In what follows path will denote a genaral path unless mentioned otherwise. Theorem 4 Let X = Dm for any integer m. Obviously. We will use E (p) to denote the number of edges in path p.rst part of our analysis we will onsider general paths in whi h all 3 kinds of edges appear. the mth edge must begin in the vertex in whi h the m 1th edge ends. L(p) = 1 if p ontains even one ghost edge. Of ourse the edges in a path must be ontinuous. The main idea of the algorithm is in the following theorem. xij = minfL(p) j p is a path from i to j and E (p) = m g Let us .e.e. the sum of the lengths of the edges in it. We will use L(p) to denote the length of a (general) path p. i. Then xij gives the length of a shortest path from i to j having exa tly m (real/self-loop/ghost) edges. i. real.e.

rst observe that the theorem is true for the ase m = 1. Indeed we de.

In this ase we have X = D2. The theorem now says that xij must be the length of a shortest path from i to j having 2 edges.ned D so that dij denoted the length of the real/self-loop/ghost edge from i to j . we . Let us now onsider the theorem for m = 2. let us he k if this worked out orre tly in our example. Before we prove this. In the example.

Finally. Thus xij gives the length of a shortest 2 edge path.e. We now sket h the idea of how the proof an be extended for larger m. note that edges of G0 are 2 edge paths of our original graph G. We an keep repeating this argument to get for larger m. ng The key observation is: ea h sum dik + dkj in the right hand side is the length of a 2 edge path from i to j . : : : . This is indeed the shortest path from Nashik to Kolhapur having 2 edges { the path passing through Mumbai. and hen e the shortest length is 1. and indeed all paths between Nagpur and Kolhapur having 2 edges must ontain some ghost edge. When X = D we have xij = minfdik + dkj j k = 1. In fa t. The . What if we now ompute X ? We would get lengths of shortest 2 edge paths in G0. x = 1. Hen e shortest 2 edge paths of G0 are shortest 4 edge paths of G. sin e we onsider all hoi es for k. you will see that all possible paths are onsidered.rst saw that x = 650. The a tual shortest path whi h goes through Pune and Satara has 3 edges. G0 ontains an edge from ea h i to ea h j of length xij . But X = D . Suppose now that we have a graph G0 orresponding to our matrix X = D . proving the laim. 2. However. and hen e the entries of D give the lengths of the shortest 4 edge paths of G. Likewise. i. we saw that x = 210 whi h is indeed the length of the shortest path having at most 2 edges. Now we prove the theorem for m = 2. and so is not to be onsidered.

and doesn't matter how many su h edges there are.nal question is. how does this relate to what we want: lengths of shortest paths with only real edges. This is what we onsider next. 34 16 54 2 2 2 2 4 4 .

with no bound on the number of edgesg We will argue that the minimum over S~ and the minimum over S are identi al. So de. we know xij is the length of the shortest path from the set S = fp j p is a path from i to j and E (p) = n0 g i.e.e. 213 Abhiram Ranade. But this argument applies to all possible paths P . xij = minp2S L(p). with E (P 0) = E (P ). any path with length less than n0. Then xij = L(P ). with m = n0. In other words. So xij L(P 0 ) = L(P ). its minimum would not hange. Now onsider P 0 obtained by adding n0 E (P ) self-loops from i to itself at the beginning of P . By Theorem 4. P 0 is now a path from i to j .e. But now P 0 belongs to the set S . i. Further. Suppose P has the shortest length amongst these. L(P 0) = L(P ). Suppose P is a path from i to j with E (P ) < n0. Suppose there exist real paths from a vertex i to a vertex j in G. Do not distribute Lemma 1 Suppose X = Dn0 denotes the matrix returned by the algorithm. sin e self-loops have length 0. On the other hand we want the length of the shortest path from the paths in the set S~ = fp j p is a real path from i to j . So L(P 0) annot be smaller than the shortest length xij in S . if we added P into the set S . 2011. i.

e. the S~0 S~. Thus. we hose n0 n 1. P~ an have at most n verti es. but the shortest path would not hange. Consider the set S~0 = fp j p is a real path from i to j and E (p) n0 g Clearly. and hen e the length of the shortest path would not hange either. We next turn to S~. and a shortest path P~ 2 S~ is also in S~0. All su h paths with ghost edges will have in. E (P~ ) n0 . We ould also allow some edgess to be ghost edges. i. This would in rease the number of possible paths in S~0. it annot pass through any vertex twi e. and hen e n 1 edges. E (P~ ) n 1. But we only have n verti es.ning S 0 = fp j p is a path from i to j and E (p) n0 g We get minp2S L(p) = minp2S0 L(p). Consider a shortest path P~ in it. Thus. Further. Hen e we have min L(p) = L(P~ ) = min0 L(p) p2S p2S Proof: ~ ~ Suppose we now allow the paths in S~0 to have self-loops. Sin e P~ is shortest.

But when we allow these hanges.nite length. and hen e they will also not hange the minimum. whi h we de. the new set we get is simply S 0.

e.ned above! We have proved that both sets must have the same minimum. ~ ~ . i. min L(p) = min0 L(p) p2S 0 p2S ~ Thus we have proved by our sequen e of dedu tions that xij = minp2S L(p) = minp2S0 L(p) = minp2S0 L(p) = minp2S L(p) But the last quantity is in fa t the value desired.

2011. Do not distribute 214 We . Abhiram Ranade.

Suppose we add n0 E (p) opies of the self loop from i to itself at the beginning of P . and a path with n verti es will only have n 1 edges. But we hose n0 to be the smallest power of 2 su h that n0 n 1. But there are only n verti es overall. What we get is a path P 0 that also goes from i to j . i.rst hara terize P . we have xij = minfL(p) j p is a path from i to j and E (p) = n0 g where we know that xij is the length of some path P~ . Sin e P is shortest. Thus E (P ) n 1. By Theorem 4. it will not return to any vertex it visited earlier. but whi h has exa tly n0 edges. But L(P 0) = L(P ) and P has . L(P 0 ) = L(P ). all the verti es on it must be distin t. Further. be ause the edges we added had length 0. Noting that the set over whi h the minimum is taken in ludes P 0. we have L(P~ ) = xij L(P 0).e. Thus we have E (P ) n0 .

Thus P~ has .nite length.

Lemma 2 Suppose X = Dn0 denotes the matrix returned by the algorithm. Then xij = 1. Be ause P is a shortest real path from i to j . sin e we only dropped length 0 edges. Thus L(P ) = xij . Thus. Putting together everything we get L(P ) L(P~ 0 ) = L(P~ ) = xij L(P 0 ) = L(P ) Thus all the terms must be equal. and hen e it annot ontain any ghost edges in it. there annot be a path from i to j having only real and self-loop edges. Sin e there is no real path from i to j . we must have L(P ) L(P~ 0 ). every path from i to j must in lude at least one ghost edge. It may ontain self-loop edges. Suppose there is no real path from a vertex i to a vertex j in G. for whi h we must have L(P~ 0 ) = L(P~ ). Thus its length is in. whi h we drop and get a real path P~ 0.nite length.

Sin e this is true for all paths from i to j . a shortest among them must also have in.nite.

you will realize that it helps to think of some systemati order in whi h to generate the permutations. Alternate Proof: 13. For example. we ould onsider generating all permutations starting with 0. if n = 3. and so on. then all starting with 1. As you know.nite length. As an example. we would like the output to be something like: 0 0 1 1 2 2 1 2 0 2 0 1 2 1 2 0 1 0 If you try to solve this problem by hand on paper. there are n! permutations of n obje ts. How do we generate all permutations starting with 0? Presumably we apply the same idea . we would like all these printed.7 Generating permutations We onsider the problem of printing out all permutations of the integers 0 to n 1.

Abhiram Ranade. Do not distribute 215 again (re urse!): we . 2011.

rst generate all permutations starting with 01. then those that start with 02 and so on. but all permutations given some starting portion of the permutation. In the intermediate stages. our problem will be slightly dierent. we dont want to print all permutations. So it will be onvenient if our fun tion takes two arguments: a sequen e P whi h has been . We will write a re ursive fun tion gPerm to print all permutations of a given set.

: : : . 4. In this notation. : : : .xed as the starting portion. and R = f1. n 1g. 3.R) will re urse. : : : . then we an all our fun tion with P being the empty string and R = f0. We have already hinted how gPerm(P. n 1g. if we want to print all permutations of the set f0. The . If we merely want all permutations of R = f0. n 1g. : : : . and a set R onsisting of the remaining elements whi h will make the remaining part of the permutation. n 1g that start with 02 we all our fun tion with P = 02.

the sequen e P annot be further extended.r.. For ea h r in R begin (a) P' = P with r appended. Our onvention will be to store P .. and it an grow by using any element of R.R together in a single array of length n. Clearly we an use arrays to store these.n-1g.R'). Thus the re ursive portion of gPerm(S. But note that if we our original problem is to print permutations of f0. and P = "0". where subtra tion is used to denote removing from the set. and so it an be printed sin e it represents a omplete permutation. Hen e we an store P. At this point. So we have des ribed all ingredients of the algorithm ex ept for how we will represent P and R. then the sum of the lengths of P and R is always n.R) an be written as follows. The base ase for the re ursion will arise when R is the empty set. (b) R' = R ..xed part P will grow. ( ) Call gPerm(P'.. end We have already given examples of this for the ases P = "".

pL-1℄ = P. So if we state the length pL of P we will know whi h part of the array is P and whi h is R.rst and R after that in the array. int pL) // A[0. out << endl. i++) out << A[i℄ << " ". This is in fa t the swap2 fun tion from Se tion 11. It uses a swap fun tion... i<n. The re ursive pro edure gPerm is as follows. int n.n-1℄ = R // print all permutations of A. A[pL. P = A[0.2. whi h merely ex hanges the values of its arguments. } else{ . void gPerm(int A[℄.pL-1℄ fixed { if(pL==n){ // base ase: R is empty for(int i=0..

Write a program that reads in an integer from the keyboard and prints it out in words. gPerm(A. int pL=0. and is thus 8. 2. the tea her enters the number of students.n. In this ase the array ontains the permutation. At the beginning. To larify. // the array in whi h P. After the re ursive all.A[pL℄). whi h is 0. followed by the marks. } // // // // 216 For ea h element A[i℄ of R extend P by appending A[i℄ re urse undo the movement The fun tion works almost exa tly as we dis ussed earlier. Abhiram Ranade.'0' is valid expression and evaluates to the dieren e in the ode used to represent the hara ters. orresponds to pL==n. R being empty. n. For example. the program then gets ready to answer student queries. swap(A[i℄. Extend the marks display program of Se tion 12. // The array only stores R. Use this to write a fun tion that takes a har array ontaining a number and return an integer of the orresponding magnitude. Then d will have the value 7. whi h we print. . i<n. 3. For this exer ise it is important to know that the odes for the digits are onse utive. After all names and marks have been entered. // array name. Then the program must prompt the tea her to enter the name of the student. Further '8' .n-1 initially gPerm(A. the program should print \three hundred and sixty eight". i++){ swap(A[i℄. int A[n℄..R are to be stored. Do not distribute } } for(int i=pL. on reading in 368. // initially P is empty. we must undo the movement to the position pL.pL+1). Our main program is main(){ int n. i++) a[i℄ = i. For the re ursion we must all with P extended by 1 hara ter.8 Exer ises 1. The base ase. So the hara ter whi h extends P must be moved to position pL.2. so its length pL = 0. length of array. i<n. if we exe ute har text[10℄ = "1729". int d = text[1℄ .'0'. for(int i=0. starting at 0. Students enter their name and the program prints out the marks they have obtained. 2011. sin e at the beginning of the all P extends from position 0 to position pL-1 of A. pL).A[pL℄).2 to use names rather than roll numbers. length of P } 13. in << n.

of all types. Abhiram Ranade. and says whether it is a valid parenthesization. Do not distribute 217 4. Spe i. Write a fun tion whi h takes a sequen e of parentheses. 2011. open and losed.

ally. and if a pair of parentheses ontains one parenthesis from another pair. with the opening parenthesis before the losing. Write a \ al ulator" program that takes 3 ommand line arguments in addition to the name of the exe utable: the . then it must also ontain the other parenthesis from that pair. parentheses should be in mat hing pairs. 5.

The se ond argument must be spe i.rst and third being double values and the se ond being a single har.

You should NOT use the re ursive de. 7. Write a fun tion whi h given a square matrix returns its determinant.5.ed as an arithmeti operator. -. Write the fun tion solveLSE of Se tion 13. The program must perform the required operation on the two numbers and print the result. * or /.e. 6. i. +.

but instead use the following properties: Adding a multiple of one row to another leaves the determinant un hanged. If the .nition of determinant. The deteminant of an upper triangular matrix (all zeros below the diagonal) is simply the produ ts of the elements on the diagonal. Ex hanging a pair of rows auses the determinant to be multiplied by -1.

rst element of the .

rst row is a zero. then ex hange rows so that it be omes non zero. Then add suitable multiples of the .

rst row to the other rows so that the .

rst olumn is all zeros ex ept the .

Similarly produ e zeros below the diagonal in the se ond olumn. Write the program to . and so on.rst row. 8.

nd shortest paths as dis ussed in Se tion 13. De.6. 9. Let p be a permutation of integers from 0 to n 1 for some n.

ne V (p) to be the integer obtained by on atenating the sequen e p. Write a program that takes a permutation p of integers from 0 to n 1 and returns the lexi ographi ally next permutation. or in the same (not ne essarily prin ipal) diagonal.7 does not generate the permutations in lexi ographi ally in reasing order. We will say that a permutation p is lexi ographi ally smaller than another permutation q if V (p) < V (q ). 11. 10. In the 8 queens problem. Your program should stop after printing k solutions (if any). you are required to pla e 8 queens on a hessboard so that no queen aptures another. The permutation generation algorithm given in Se tion 13. Modify it to do so. Hint: modify the permutation generation program. Write a program to solve the analogous n-queens problem. or in the same olumn. For those who do not know hess: a hessboard has 8 rows and 8 olumns. where k is spe i. and two queens apture ea h other if they are in the same row. Hint: try out a few permutations to dedu e the relationship between a permutation and the lexi ographi ally next permutation.

.ed by the user in addition to n.

for example. other urves are also often used. One way to smooth a orner is to lo ally ins ribe a ir ular ar that is tangential to edges forming the orner. You might have observed that most physi al obje ts are designed to have smoothed rather than sharp orners. whi h have been used in the design of automobile bodies. 218 Abhiram Ranade. 2011. However. Do not distribute 12. A Bezier urve of order n is a parametri urve de. One su h family of urves are the Bezier urves.

p (t). : : : . the base ase: Bp (t) = p To ompute Bp .ned by using n ontrol points p .:::. we . The parameter whi h we will denote by t varies between 0 and 1. pn.p (t). This point an be determined re ursively as follows.:::. First. and for ea h value of t we get one point Bp .

p (t) = Bq .:::.e.rst determine points q . 1 1 1 1 n +1 +1 1 n 1 n 1 n .q (t) Write a program whi h re eives points on the graphi s anvas and plots a Bezier urve through them.:::. : : : . qn 1. where qi = tqi + (1 t)qi i. qi is the point dividing the line segment pipi in the ratio t : 1 t. Now we have: Bp . Experiment for dierent values of n.

perhaps we should be able to de lare variables a.b). Wouldnt it be ni e if you ould refer to sets in your program by giving them names and write something like = union(a. but the language should merely supply us the fa ilities to write su h fun tions and de. The fun tion will we written by us. Presumably. being able to write any program is dierent from being able to write any program onveniently. we should be able to perform set operations on set type data.b.Chapter 14 Stru tures and Classes By now. This is not to say that C++ should supply us with a built-in data-type for representing sets. where a. say taking the union of two sets. just as we an de lare variables p. However.b are sets. Suppose for example that you are writing a program involving sets.b? Basi ally. or a built-in fun tion for omputing union.. Just as we routinely perform arithmeti on double data. you have learnt enough programming language features to be able to write any program you might wish to write. your program will need to keep tra k of several sets. and where we want to be ome the set whi h is the union of a. and perhaps perform operations on them. of type set.r of type double.q.

ne su h data types. More generally. it might be desirable to have data types for representing any entity that is important in the program that we are writing. if we are writing programs about books in a library. we should be able to de. For example.

we should be able to operate on su h obje ts. This hapter takes a step towards understanding this approa h. The .ne a Book data type. by using fun tions whi h we would write. And of ourse. This idea is the beginning of an approa h to programming alled Obje t-oriented programming. su h that variables of type Book will hold information about a book.

a library number. We begin by dis ussing the basi ideas of stru tures. for a book we might want the olle tion to ontain the name. A stru ture. information about who has borrowed it and so on. an array name does refers olle tively to lots of elements. as we will dis uss in this hapter provides what we want: it allows us to group together data of dierent kinds into a single olle tion whi h we an olle tively refer to by a single name. This is somewhat like an array. For example. name of the author. We will show several examples. pri e. ex ept that now we want a name to refer to a olle tion of elements whi h might be of dierent types. and then dis uss at length a stru ture using whi h 3 dimensional ve tors an be ni ely represented 219 . Using stru tures will turn out to be very natural for many appli ations.rst step in this approa h is to olle t together all the information on erning an entity and be able to refer to the olle tion by a name.

Do not distribute 220 and elegantly manipulated in programs.2. We also dis uss how to build a stru ture to represent the queue like fun tionality we saw in Se tion 12. 2011. Abhiram Ranade.5. whi h . We then dis uss some advan ed features of stru tures.

14.nally takes us to the notion of lasses.1 Basi s of stru tures A stru ture de.

. } This statement says that the name name-of-stru ture will denote a new type of variable. but it is often ustomary to apitalize the . A variable of type name-of-stru ture will be a olle tion of sub-variables or members whose names and types are as given.. member2-name member2-type.nition has the following general form: stru t name-of-stru ture { member1-name member1-type.. The rules for hoosing names for stru tures or members are the same as those for ordinary numeri al variables. or a new data type.

rst letters of stru ture names. As an example. here is how we might de. whi h is a onvention we will follow.

stru t Book{ har title[50℄. har author[50℄. int a essionNo. double pri e. int borrowerNo. bool borrowed.ne a stru ture to store information about a book. Note that a stru ture de. }.

nition does not by itself reate variables or reserve spa e. But we an use it to de.

a essionNo. This statement is very similar to a statement su h as int pqr.50). . of type Book.ne variables as follows. xyz. A member of a stru ture variable an be referred to by joining the variable and the member name with a period.getline(pqr. xyz. Spa e is also reserved in memory for ea h variable. So a total of 113 bytes is reserved ea h for pqr and xyz. and so we may write: xyz.a essionNo = 1234. and pri e.g. e. Assuming 4 bytes are used to store an int and a double. in. xyz. { it auses variables pqr and xyz to be reated. we will need 12 bytes to store the members a essionNo. A bool data type will typi ally be given 1 byte. In this spa e the various members of the stru ture are stored. Book pqr. Su h referen es behave like variables of the same type as the member. borrowerNo.title. and 50+50 bytes to store the members title and author.

Abhiram Ranade. Do not distribute 221 The . 2011.

rst statement will store 1234 in the 4 bytes of the 113 bytes reserved for xyz.title refers to the . In the se ond statement. the referen e pqr.

Just as we an read a hara ter string into a dire tly de.rst of the two har arrays in pqr.

so an we into this member of pqr. If in ase the user typed \The Sel.ned har array.

firstname[0℄ would then take the value 'T' as expe ted.sh Gene". We an initialize stru tures in a manner similar to arrays. Assuming Book de. then this would be read into pqr.title. and so for instan e pqr.

One stru ture an be opied to another using an assignment. 350.3.0. enter. double y..2}. Here for example is a stru ture for storing information about a ir le. stru t Point{ double x. 1.9. } Now the following natural program fragment is quite legal. enter.y = 0. }.5. by writing something like Point p1. 1. "Bertrand Russell". We may reate instan es of this stru ture in the manner des ribed before. 1235. 1. We ould also have a omplished this by writing: Cir le 1 = {{0. double radius.e. For example. assuming 1 is as de.radius = 3. Cir le 1.x = 0. true. 5798}. We are allowed to have one stru ture be ontained in another. stru t Cir le{ Point enter.5.00.2. Here is a stru ture for representing a point in two dimensions.ned as above we might write Book b = {"On Edu ation". i.9}. This will opy elements of the initializer list to the members in the stru ture.

we an further write: Cir le 2. This auses every . 2 = 1.ned above.

eld of 1 to be opied to the orresponding .

. In a similar manner we ould also write: Point p = 1. 2. enter = p. enter.eld of 2.

Abhiram Ranade. 2011. Do not distribute 222 The .

enter. The se ond opies every member of p to the orresponding member of 2. enter to the orresponding members of p. We .rst statement opies every member of 1.

nally note that variables an be de.

ned in the same statement as the de.

nition of the stru ture. we ould have written stru t Cir le{ Point enter. double radius. } C1. whi h would de. For example.

Thus in the blo k in whi h it appears. it an be used at all points following its de.1.ne the stru t Cir le as well as an instan e C1. 14.1 Visibility of stru ture names A stru ture name is available for use as per the same rules as for the names of variables.

nition. it might shadow names de. Also.

ned in blo ks outside the blo k in whi h the de.

nition appears. or it might in turn be shadowed by names de.

ned in blo ks ontained in the urrent blo k. If a stru ture is going to be used in more than one fun tion. it must be de.

ned outside both the fun tions. The de.

nition must textually appear before the fun tions in the .

Assuming the de. In Se tion 12. We see examples next. We will see examples of this in Se tion 14. It is also possible to return a stru ture. unlike the name of an array.2. we wrote a program to de ide if any of a set of ir les interse t.1.2 Stru tures and fun tions It is possible to pass stru ture variables to fun tions.2. Just like numeri al data types.1).6. The key point to be noted is that the name of a stru ture denotes the ontent of the asso iated memory. or by referen e (Se tion 11. A key part of the program was the ode to determine whether two ir les interse t. Thus the behaviour of stru ture for opying and passing to fun tions is like ordinary numeri al data types rather than like arrays. whi h denotes the address of the asso iated memory. stru tures an be passed by value (Se tion 9.le. 14.2).1.

5}. } The fun tion ould be alled from the following fragment of the main program: Cir le 1 = {{0.nition of stru ture Cir le as given above. . bool q=interse ts( 1.2.0}.2}.x.2) <= pow( a. enter.3. else return false. Cir le b){ if(pow( a. enter.y- b. bool interse ts(Cir le a.y. enter.x- b. we an he k for interse tion using the following fun tion.r+ b. 2={{0.0}.2)) return true. 2).2)+ pow( a. enter.r.

with 1 as de. Here is an example.r = . So if this is alled from the main program as expand( 1. the entire memory region of 1.x. the ir le 1 of the alling program would not be ae ted. Abhiram Ranade. } This would ause the member . in this ase just a single bit. 2 is opied into the region of a. 2011.e. enter. Do not distribute 223 and it would set q to true. Thus even if the fun tion were to hange a. Note that for the pro edure all. Note further that when the fun tion exe ution ends. i. void expand(Cir le & . is opied ba k. b in the a tivation frame of the all. double fa tor){ .0). we would have to mark the orresponding parameter as a referen e parameter. only the result.r to s ale up by a fa tor fa tor. If we want the values of the arguments to hange. the ir le enter would not hange but the ir le would just be ome bigger.2.r * fa tor.

4. there is another important bene. Besides enabling the argument to be hanged.ned above. then the radius of 1 would be ome 6.

Thus this will likely be faster. double fa tor){ (* ).t of passing an argument by referen e.3 Pointers to stru tures The \address of" operator & and the dereferen ing operator * an be used with stru tures and pointers to stru tures respe tively.1. } As you would . Thus we ould write the expand fun tion using pointers as follows. typi ally) is sent.r * fa tor.r = (* ). if the stru ture is very large. The value of the argument is not opied over from the alling fun tion to the alled fun tion. 14. instead only the referen e (a single word. void expand2(Cir le * .

the .nd natural.

is de lared to be of type Cir le*. The expression * dereferen es the pointer getting ba k the ir le itself whose address was passed. The member r of this ir le is modi.rst parameter . i. pointer to Cir le.e.

where pqr is a stru ture pointer appear very frequently.0}. This ould be alled from a main program su h as follows. whenever a member of the stru ture pointed to by pqr is to be a essed. expand(& .ed.e. } If stru tures are passed to fun tions by pointers.2}.3. i. then expressions su h as (*pqr). a dierent operator is de. So for this.2. main(){ Cir le 1={{0.0).

Thus the fun tion expand2 ould also be written as follows.ned in C++. } . you may simply write pqr->ab . double fa tor){ ->r = ->r * fa tor. void expand2(Cir le * .ab to a ess member ab of (*pqr). Instead of writing (*pqr).

Abhiram Ranade. Do not distribute 224 If for some reason you wanted to refer to the x oordinate of the enter of the ir le to whi h you have a pointer as above. the -> operator is more readable than the derereferen ing and \. you would write it as -> enter. 2011. Clearly." ombination. However.x as you might expe t.4 Constant referen es We have mentioned that passing stru tures by referen e has the bene. it is even better not to use pointers if possible and pass the stru ture by referen e instead. 14.1.

it is useful to indi ate our intent. So indeed we should onsider passing stru ture arguments by referen e to every fun tion. When our goal is to merely avoid opying and we do not want to hange the referen e parameter.t of not having to opy the stru ture at the time of the all. this an be done by using the pre. In C++.

r+ b. enter.r. enter. So for example we might write bool interse ts( onst Cir le & a. onst Cir le & b){ if(pow( a.2)) return true. enter.y.x- b.x.x onst before the parameter de laration.2)+ pow( a. } This style has the bene.2) <= pow( a.y- b. else return false. enter.

t of preventing the arguments from being opied. and in addition onveniently tells a human reader that the parameters will not be modi.

[5℄.x refers to the x oordinate of the enter of the .1. It also has another desirable ee t whi h will be dis ussed in Se tion 14. Book library[100℄.5 Arrays of stru tures Note that we an make arrays of any data type.2 14.ed.2. For example. We an refer to members of the elements of the arrays in the natural manner. Cir le [10℄. For example. enter. we ould make an array of ir les or books if we wished.

y oordinates of the enter and for the radius. Similarly library[96℄. We assume that the fun tion interse ts has been de.fth ir le in .title[0℄ would refer to the starting letter in the title of the 96th book in library. rather than separate arrays for storing the x.2. Let us now write the program from Se tion 12.6 using an array of ir les.

ned as above. and before that the stru tures Point and Cir le have been de.

Following the fun tion. in >> n. Cir le ir les[n℄. main(){ int n. . the main program an be written as follows.ned.

or in so alled spheri al oordinates.i<n. } } 14. This program will deal onsiderably with 3 dimensional ve tor quantities su h as positions. Abhiram Ranade.x >> ir les[i℄. enter. we onsider the . enter.y >> ir les[i℄.r. A ve tor in 3 dimensions an be represented in many ways. For example.i++) // read in all data. i++){ for(int j=i+1. in >> ir les[i℄. j++){ if (interse t( ir les[i℄. 2011. i<n. Do not distribute 225 for(int i=0.2 Representing 3 dimensional ve tors In the next hapter we will see a program whi h deals with motion in 3 dimensional spa e." <<endl. and a elerations. For simpli ity. ir les[j℄)) out << "Cir les " << i << " and " << j << " interse t. So we will design a stru ture whi h makes it onvenient to represent su h quantities. for(int i=0. // Find interse tions if any. j<n. we ould onsider it in Cartesian oordinates. or ylindri al oordinates. velo ities.

We will all our stru ture V3 and it an be de. Thus we will have a omponent for ea h spatial dimension. Clearly our stru ture must hold these 3 oordinates.rst alternative: Cartesian oordinates.

We should put this outside the main program. If the program is organized into many .z. }.y.ned as: stru t V3{ double x.

les. this should go into a header .

le. whi h an then be in luded in all other .

x. V3 b){ return make_V3(a. return v.les whi h need this stru ture. v. whi h will be opied ba k to the alling program. a.b.x = p. double q. double r){ V3 v.y. } .y = q. First we will write a fun tion whi h will onstru t a V3 stru ture given values of the 3 omponents. The real use of this fun tion is in the following fun tion whi h allows us to add two V3 numbers.x+b. v.z = r. v. } Note that this returns v.z+b. V3 make_V3(double p. a. V3 sum(V3 a.z).y+b.

= sum(a.x*a.0.2.x + a. 226 Abhiram Ranade.1 Operator overloading The addition operator.5}.b). Do not distribute Thus we an now write a ode fragment like the following. Similarly we an write fun tions whi h will perform other arithmeti operations. This will make be the ve tor with omponents 4. is not automati ally de. rather than =sum(a.b).y + a. wouldnt it be ni er if we ould just write expressions su h as =a+b. +.4.z*a. 2011.2}.? This is easily arranged! We an overload operators so that they will work with our ve tors! 14. . A natural fun tion that will be needed is the length of a ve tor. V3 a={1.4. b={3. double length(V3 a){ return sqrt(a.7.y*a. } Ideally.z). you might wonder.

But we an de.ned for all data types.

ne it! For this note .

rst that C++ really treats operators as fun tions of two arguments. For ordinary fun tions. the arguments are supplied in parentheses. the operator appears in between the arguments. However. and hen e it is alled an in. for an operator su h as +. separated by ommas.

x operator. To de.

V3 b){ return make_V3(a. a.x+b. you only need to note that the name asso iated with + is operator+.y+b. a.x.ne the + operator for V3 numbers. } Similar de. V3 operator+ (V3 a.z). whi h is what you need to overload.y. Thus it suÆ es to write the following.z+b.

by writing operator. This merely s ales ea h omponent. This su in tly expresses the kinemati s formula s = ut + t . a. a.x*t. Noti e that if s.5.. This is also a binary operator. It is ommon to multiply a ve tor by a s alar. but in this ase the .instead of operator+.u. If we want to be able to write this using the operator * we ould arrange it by writing the following. V3 operator*(V3 a. then we an ompute s by writing s = u*t + a*t*t*0. double t){ return make_V3(a. initial velo ity and (uniform) a eleration. An interesting ase is that of the << operator. and t denotes the time.y*t.nitions an be made for .a are ve tors denoting the distan e overed.z*t). This is left as an exer ise.

. whi h really should be read as ( out << z1) << z2. Further. so they must be passed by referen e.rst operand is of type ostream. the .. if we want to write expressions su h as out << z1 << z2. We have seean earlier that stream variables annot be opied.

out<<z1 should evaluate to out.rst part. This is what the following de.

nition implements. 1 2 2 .

2011. "<< v. the value is returned by referen e. Abhiram Ranade. return ost. } Note that the value returned would normally be opied ba k. be ause opying data of type ostream is not allowed. Now if a. Do not distribute 227 ostream & operator<<(ostream & ost.z << ")".y << ". V3 v){ ost << "(" << v. Again.b were de. hen e the type of the return value is ostream &.x << ". "<< v.

we have passed the V3 parameters by value. 5) b: (3. we should add the quali. 4. Further. 14. and this would print a: (1. 2) The exer ises ask you to similarly overload the >> operator so that a triple of numbers an be read into a V3 variable.2.ned as in the main program above. We should onsider passing by referen e.2 Pass by value or by referen e In the entire dis ussion above. 0. be ause that would prevent the need to opy the argument values to the parameters. then you ould write out << "a: "<< a <<" b: "<< b << endl.

er onst wherever we know that the orresponding parameter will not be modi.

z+b. we ould have written: V3 operator+ (V3 onst& a. then it annot be onstant.y. As an example. a. there is no question of it getting modi.1 that if an argument is passed by referen e.ed. that remark does not apply when the referen e is de lared onst.x.2. Sin e the parameter is onstant. a. However. V3 onst& b){ return make_V3(a.z).x+b. } We noted in Se tion 11.y+b.

and hen e the problems as mentioned in Se tion 11. with the above de. In other words.ed.2.1 would not arise.

2.z >> a.x >> u.2).y >> a.1 we pla e the de. 14.7) as expe ted. in >> u. we an write the all make V3(1.3 Putting it together We an use the fun tions and stru ture that we have developed to write a main program as follows. main(){ V3 u.5 << endl.a.5) + make V3(3.y >> u.4. out << u*t + a*t*t*0.1.4.nition. and it would return the V3 ve tor (4.0. } Following the dis ussion in Se tion 14.x >> a.z >> t. double t.

nition of the stru ture V3 at the top of the .

Then we pla e all the fun tions. and then .le.

nally the main program. We an then ompile this .

This will ask the user to give the initial velo ity. . the a eleration. and the time duration.le and run it. and the distan overed will be printed.

on e you de. we organize data into a olle tion rather than have lots of variables lying around.3 Stru tures: advan ed features We ould think of a stru ture as merely a me hanism for managing data. 2011. However. Do not distribute 14. 228 Abhiram Ranade.

it be omes natural to write fun tions whi h manipulate the data ontained in the stru tures.ne a stru ture. You might say that on e we de.

Had we de.ned V3. it is almost inevitable that we write fun tions to perform ve tor arithmeti and ompute the Eu lidean length.

you might onsider these fun tions to be as important to the stru ture as are members of the stru ture. should we make the fun tions a part of the stru ture itself? The de. we might have found it useful to write a fun tion that performs the bookkeeping needed when a book is borrowed. Indeed. say a book (in a library). So perhaps.ned a stru ture to represent some other entity.

In the more modern de.nition of stru tures you have seen so far really omes from the C language.

as it is in the C++ language.nition of stru tures. the de.

At a high level. the more general de.nition of stru tures has been extended so that it an also in lude fun tions.

Member fun tions an be spe ial and ordinary.nition of a stru ture is the same as before. the so alled onstru tor and destru tor fun tions. We will shortly des ribe in general how member-fun tions are spe i. stru t name-of-stru ture { member-des ription1 member-des ription2 .. In addition there an be as many ordinary member fun tions as you want. now. a member-des ription may denote a member-fun tion. } But.. in addition to being able to denote a pair member-type member-name as before. There an be two kinds of spe ial member fun tions.

ed and alled. but let us .

rst see an example. Here is how our stru ture V3 will appear in this new de.

} double length(){ return sqrt(x*x + y*y + z*z). double q.nition style. y = 0.z.y. z = r. V3(double p. } V3(){ x = 0. double r){ x = p. } V3 operator+ (V3 b){ // onstru tor 1 // onstru tor 2 // ordinary member fun tion length // ordinary member fun tion operator+ . stru t V3{ double x. z = 0. y = q.

y*t. } V3 operator. } V3 operator* (double t){ // ordinary member fun tion operator* return V3(x*t.. There is no destru tor fun tion. 229 return V3(x + b. y-b. In general. 2011.. z-b. operator*. y+b.y. and the ordinary member fun tions length. You an spe ify as many onstru tors as you want. the member-des ription for a onstru tor fun tion for a stru ture with name stru ture-name has the following form.z).x. z*t).z).x. operator-.3. } This ontains two onstru tor fun tions. parameter2-type parameter2. Constru tors are used for de. operator+. Abhiram Ranade. analogous to the make V3 fun tion we had earlier.){ body }. z+b. stru ture-name is the return-type as well as the name of the fun tion. .(V3 b){ // ordinary member fun tion operatorreturn V3(x-b.1 Constru tor fun tions A onstru tor fun tion is used to reate an instan e of the stru ture.y. so long as the list of parameter types are dierent for ea h onstru tor. 14. we will dis uss destru tors later when we need to. stru ture-name (parameter1-type parameter1. In this. Do not distribute }.

without using the \.z omponents set to 1.0. As you will see this will reate a variable ve 1 with its x..3." notation. Next. A all to a onstru tor exe utes as usual by reating an a tivation frame.0. by writing: stru ture-name(argument1. argument2.0.. Then something unusual happens: a nameless variable of type stru ture-name is reated.0. ve 2=V3().) Here is an example in whi h we reate two variables by respe tively alling our two onstru tors.y. . Then the arguments are evaluated and are opied to the orresponding formal parameters.0. the body of the onstru tor is exe uted and when exe ution . and a variable ve 2 with all its omponents set to 0. Its data members an be a essed in the body of the onstru tor by using the member names themselves.2.ning variables of the given stru ture type. They may be alled in the natural manner.0). i.3. V3 ve 1=V3(1.2.e.

An a tivation frame is reated and the argument values.0.0. As noted a nameless stru ture V3 is also onstru ted. 3. this is a all to onstru tor 1.0) in our example would exe ute. Let us now see how the all V3(1. Clearly. Then the body of onstru tor 1 starts exe ution. sin e there are 3 arguments.0.0 are opied to the orresponding formal parameters p. 2. 1. this nameless variable is returned as the result.0.nishes.q. The .2.3.r.

rst statement of the body. sets the x member of the nameless . x = p.

but on examining its body. In general. If one stru ture is nested inside another. This returned value..2 Ordinary member fun tions The ordinary member fun tions length.3. 1. The exe ution of the all happens as follows.0.. the variable var treated just like an argument. Suppose var is a variable or expression of type stru ture-name. using the same \. then the onstru tor exe utes slightly dierently. are opied over to the orresponding parameters. . 14. 3. .. Clearly. Ea h member fun tion is deemed to have an impli it referen e parameter of type stru ture-name.z all to 0. argument1. If the argument list is empty you are expe ted to not give it at all.. parameter2-type parameter2. Following this.2.." notation used for a essing data members. it means something quite dierent: it de lares ve 2 to be a fun tion that takes no arguments and returns a result of type V3.) You are indeed expe ted to think of a member fun tion all as being similar to a essing a data member. An a tivation frame is reated for the exe ution. Abhiram Ranade. Then the member fun tion fun tion-name is alled on it as: var. The variable var is onsidered as a referen e argument for this impli it parameter.7. 2. the nameless obje t is returned as the result.. Thus the variable ve 2 will have all its 3 members be 0.0. operator+ and so on in V3 will play the role of similarly named fun tions of Se tion 14.fun tion-name(argument1.y.){body} A member fun tion is expe ted to be alled on a variable of the given stru ture type. argument2. .. ve 2. The expressions var. is opied to the variable ve 1. the members y and z are set to the values q and r respe tively.. 2011.. are evaluated. as we dis ussed in Se tion 9. the member-des ription of an ordinary member fun tion for a stru ture with name stru ture-name has the following form. you will see that it sets all 3 members x.0. 2.2. in our example. .y.4. The values of the arguments argument1. Note that if you write V3 ve 2().3. as in the onstru tion of ve 2 above. It takes no arguments. what follows the variable name is used as the argument list to all an appropriate onstru tor. 4.z members. ve 1 will have 1. The se ond onstru tor exe utes similarly. For the exe ution. Similarly. This and other nuan es are dis ussed in Se tion 14. The more ustomary way of writing the above statement is V3 ve 1(1.0 as its x. Do not distribute 230 stru ture to the value of the parameter p. return-type fun tion-name (parameter1-type parameter1. As you an see. argument2.1.0).0 and 3.

p. V3 p(1. and hen e the names x.3). 231 Abhiram Ranade.2.operator+(q).z in the body of length will refer to p. the names of the data members by themselves are onsidered to refer to the orresponding members of the impli it parameter.length() << endl. s = p+q.3 in the . r.y. Let us now see an example. whi h have been respe tively initialized to 1. Do not distribute 5. any hanges we might make get re e ted in var.e.5). inside the body. Note that sin e the impli it parameter is a referen e parameter.length().x. out << p. the impli it parameter will be p.2. q(3.z. r = p.s. 2011.p. // more ustomary form In the all p.y.4. You an think of the impli it parameter as providing a ontext. The body of the fun tion is exe uted. i.

Thus r will be ome the stru ture with omponents 4.y. In the next statement.y. 1.4. and the the parameter b will take the value q.e.y.z. p will again be the impli it parameter. z+b.e. Thus the names x.b. 14. Also b. i. Thus.rst statement.x. p the statement return sqrt(x*x + y*y + z*z). y+b.p. The more ustomary way of using the fun tion operator+ is of ourse to write the binary in.2. 3.p.x.q.z.e.x.z will refer to p.y. Thus the statement statement return V3(x+ b.x. will return sqrt(1*1+2*2+3*3).operator+(q).q. i.8) to be returned.b.8.5.6.3.z will refer to q.y. i.z) will ause V3(4. in the all p.6.

This will ause s to also be set to a ve tor with omponents 4. as is shown in the next line.4 Additional issues We now dis uss some aspe ts of stru ture de. s=p+q. 8..x operator +. 6. 14.

1 Call by referen e and onst de laration It is possible to pass arguments to member fun tions by referen e. Thus we ould have de. Note that a member fun tion is invoked on some instan e of the stru t. For this.2).e. Further note that we an de lare parameters to be onst.4. The me hanism for this is exa tly the same as for ordinary fun tions (Se tion 11.nition not dire tly seen in the V3 example odes dis ussed so far. after the parameter list of the fun tion but before the body. we need to pla e an additional onst keyword. i. that they will not hange during exe ution of the member fun tion. 14. it is possible that the member fun tion does not hange that stru t either.

V3 operator+ (V3 onst & b) onst { return V3(x+b. y+b. z+b.y.x.ned operator+ of V3 as follows.z). // noti e there are 2 onst's .

4. Abhiram Ranade. 2011. z = r. The se ond onst. in this ase 0. or upto 3 arguments { parameters orresponding to arguments that have not been given will get the default values. y = q. Similar hanges should be made to the other member fun tions in V3. we ould have bundled our two onstru tors for V3 into a single onstru tor by writing V3(double p=0. For example. double q=0. Do not distribute 232 The onst in the de laration of the parameter b merely states that b will not hange. double r=0){ x = p. 14.2 Default values to parameters Parameters to member fun tions an also be given default values. } Now you ould all the onstru tor with either no argument. Note that if you in lude our new onstru tor in the de. after the parameter list says that the impli it argument does not hange either.

Say you spe i.nition. you annot in lude any of the onstru tors we gave earlier.

Then a all V3() would be ambiguous. or the body of the new onstru tor in whi h all 3 parameters are initialized to their spe i.ed the new bundled onstru tor and also onstru tor 2. it would not be lear whether to exe ute the body of onstru tor 2.

4.3 Default Constru tor You may wonder what happens if our stru ture de.ed defaults. 14.

but with an empty body. This onstru tor takes no arguments. In this ase. C++ supplies a default onstru tor. Su h onstru tors would be supplied by C++ for all the stru ts we de. and its body is empty: for V3 the default onstru tor would have been exa tly like our onstru tor 2.nition ontains no onstru tor at all.

The term default onstru tor is a tually used more generally: it has ome to mean a onstru tor that an be alled with no arguments.ned in Se tion 14.1. even if su h a onstru tor has been expli itly de. sin e we gave no onstru tors for them.

as well as our bundled onstru tor would be alled default onstru tors. Thus for V3 our onstru tor 2. as we remarked earlier. Of ourse. 2 default onstru tors annot be spe i.ned by the programmer.

ed simultaneously for any stru ture. Earlier we remarked that \Constru tors are used for de.

for example.ning variables" { this should be read in a strong sense: variables an only be reated using onstru tors. Thus it is only be ause of the default onstru tor supplied by C++ that we were able to onstru t stru ture variables in Se tion 14.1. We note further that a default onstru tor is needed if you wish to de.

ne arrays of a stru ture. Note that C++ does not supply a default onstru tor if you give any onstru tor whatsoever. So if you de. be ause ea h element of the array will be onstru ted only using the default onstru tor.

ne a non-default onstru tor (i. Thus you would not be able to reate arrays of that stru ture. a onstru tor whi h must take at least one argument).e. . then the stru ture would not have a default onstru tor.

2011. Do not distribute 233 The default onstru tor is important also when we nest a stru ture inside another. 14.4 Constru tors of nested stru tures Consider the Point and Cir le lasses of Se tion 14. de. Abhiram Ranade.4.1. We dis uss this next.

y. Suppose now we hange our de. As dis ussed above.}. the onstru tor reated by C++ will all default onstru tors of all the members as well. the C++ onstru ted onstru tor for Cir le will all the default onstru tor for Point. So in our ase. Note however. the default onstru tor for Cir le would be alled. that this onstru tor must onstru t all the members of Cir le.ned as stru t Point{double x. C++ will reate one for us. stru t Cir le{Point enter. Sin e we did not supply a onstru tor. Consider what happens when we exe ute Cir le . double radius. To a omplish this.}.

Point(double p. and hen e is not a default onstru tor. Further. stru t Point{ double x. Note that this onstru tor takes two arguments. The . double q){x=p. y=q.y.} }. be ause a onstru tor is given for Point C++ will not reate any onstru tors for Point.nition of Point so that it has a onstru tor.

radius = r. } }. The reason for this is a bit involved but worth understanding. and not rely on C++ to supply one. Here is a possible attempt. Unfortunately. The phrase \a stru ture of type Cir le is reated" is interpreted very strongly { if the stru ture . this attempt does not work. This is be ause the onstru tor reated for Cir le would expe t a default onstru tor to be present for Point.y). you might de ide to write your own onstru tor for Cir le. double y. a nameless stru ture of type Cir le is reated. stru t Cir le{ Point enter. We said that before the onstru tor body exe utes..rst observation. double radius. double r){ enter = Point(x. then. whi h is used as a ontext to the exe ution of the body of the onstru tor. is that now you would not be write Cir le . Cir le(double x. To over ome this problem.

Do not distribute is reated. you an assume that C++ will have reated a default onstru tor whi h does nothing. so there is no problem for this member. C++ will attempt to look for a default onstru tor.e. Thus a onstru tor will already have been alled to onstru t every member of Cir le even before the Cir le onstru tor body starts exe ution! In the absen e of additional information. the onstru tors must already have been alled for them. not . 2011. But for the member enter. 234 Abhiram Ranade. its members must also be in a \ reated state". i. the members will be reated using their default onstru tors. For the member radius.

be ause it is likely faster. In general. where x. radius(r) Note that in our example. 1 . and generate an error. The initialization list of a onstru tor says how the data members in the nameless stru ture should be onstru ted before the exe ution of the onstru tor itself an begin. radius(r) { // empty body } }. the initialization list onsists of omma separated items of the form member-name(initializing-value) This will ause the member member-name to be initialized dire tly using initializing-value.y). all the work got done in using the initialization lists. double radius. the initialization list ould also have been: enter(x.y)).nd it. 1 14. stru t Cir le{ Point enter. If the initializing value alls a onstru tor.4. The text following the : to the end of the line in the above ode is an initilization list. for our Cir le onstru tor. Thus in this ase the ode says that enter should be onstru ted using the onstru tor all Point(x.y are from the parameter list of the Cir le onstru tor. if we wish.5 Initialization lists The orre t ode whi h will use the non-default onstru tor of Point is as follows. double y. Thus. The problem an be solved using initialization lists. 2 Or you an equally well assume that members whi h are fundamental data types do not need to be onstru ted. Similarly the member r of the Cir le being onstru ted is assigned the value r. double r) : enter(Point(x.y). Cir le(double x. 2 Whenever possible you should use initialization through initialization lists. so the body is empty. Note that we ould hoose to initialize only some of the members using the initialization list and initialize the others in the body. just the omma separated arguments ould be given. then instead of writing out the all.

as follows.y. Algorithmi ally.y using initialization lists.b.7 Stati data members Suppose you wish to keep a ount of how many Point obje ts you reated in your program.4. } Point(double x1. then we would write it as follows.y. we merely keep an integer somewhere that is initialized to 0. and not as assignment to the members. On the other hand. y(y1) { // empty body } } Noti e that we have given values to members x. This is indeed possible through the use of stati data members. This is treated as initialization of the members. So initialization lists are useful for this as well. double y1) : x(x1). The question is: how should this ode be organized. // a tually defines int main(){ Point a. and then in rement it when we reate an obje t. Point(double x1. this is not diÆ ult at all. } . but not hanged subsequently. 2011. in the onstru tor of the previous se tion. } }. the values were assigned in an assignment inside the body { that is not allowed if the member is de lared onst.2). stru t Point{ double x. y(y1){ ounter++. double y1) : x(x1). This write-on e strategy of programming is very omforting: it is easier to reason about a program if you know that the values on e given do not hange. Abhiram Ranade.6 Constant members Sometimes we wish to reate stru tures in whi h the members are set at the time of the initialization. we need to de ide where to pla e the ounter. Do not distribute 235 14. stru t Point{ onst double x. 14. out << Point:: ounter << endl. int Point:: ounter = 0. It would seem natural that the ounter be somehow asso iated with the Point type. (1. If we want our Point stru ture to have this property.4. stati int ounter. First. // only de lares Point(){ ounter++.

Abhiram Ranade. 2011. It is de lared by pre. Do not distribute 236 A stati data member is a variable asso iated with a stru t type.

Note that while there will be a member x and a member y in every Point stru ture reated through either of the onstru tors. Inside the de.xing the keyword stati to the de laration. there is only one opy of the variable ounter.

nition of Point. outside the de. the variable ounter an be referred to by using the name ounter.

nition a stati variable must be referred to by pre.

xing its name by the stru t name and ::. So in this example we have used Point:: ounter. There is a subtlety asso iated with stati data members. The de.

a stru t de.nition of the stru ture Point does not a tually reate the stati data variables.

8 Stati member fun tions You an also have stati member fun tions. 14.4. Hen e we need the statement marked \a tually defines" in the ode above. in the above ode we ould have added the following stati fun tion de. without allo ating any storage.nition is merely expe ted to reate a type. For example.

nition of resetCounter to the de.

stati void resetCounter(){ ounter = 0.nition of Point. } // note keyword ``stati '' Stati member fun tions an be referred to by their name inside the stru ture de.

nition. and by pre.

xing the stru ture name and :: outside the de.

e. Further. for a stati member fun tion. i. the obje t on whi h the non-stati member fun tion is invoked. However. So we an write Point::resetCounter() in the main program if we wish to set Point:: ounter to 0. but they are invoked by themselves. Note that in non-stati member fun tions we use the names of the non-stati members by themselves to refer to non-stati members of the impli it parameter. there is no impli it parameter. Thus it is an error to refer to non-stati members by themselves in the body of a stati member fun tion.4. 14.nition. stati member fun tions are not invoked on any instan e.9 The this pointer Inside the de.

be ause we an get to the members of the nameless stru ture or the impli it parameter by using the names of the members dire tly. The following member fun tion ode ould be added to the de. it should be noted that we ould use this too. Normally. However. we do not need to use this pointer. thus we ould have written the length member fun tion in V3 as double length(){ return sqrt(this->x*this->x + this->y*this->y + this->z*this->z). and to the nameless stru ture in ase of onstru tors. and then return the ir le with the bigger radius. The fun tion would need to just ompare the radii. } But of ourse this is not really a good use for this! Suppose we wanted to have a member fun tion bigger in Cir le whi h would take another Cir le and return the bigger of the two ir les.nition of any ordinary member fun tion. the keyword this is a pointer to the impli it parameter.

.nition of Cir le above.

14. We will put all the data related to the queue into a single stru ture. Abhiram Ranade.2. This will have two bene. 2011.5.radius) ? *this : . Do not distribute 237 Cir le bigger(Cir le ){ return (radius > . At the heart of this program are the ideas of using the array board as a queue.5 A queue data stru ture We revisit the taxi dispat h program of Se tion 12. Thus we return *this. whi h will have member fun tions whi h allow elements to be inserted and removed. } We must return the impli it parameter if its radius is bigger than the radius of the argument ir le.

The initialization of emptyBegin. Figure 14.2. the logi of managing the stru ture will get separated from the logi of using it. You an note lear parallels between this and the ode in Se tion 12.ts. the stru ture whi h we will all Queue. it will be mu h easier to use this stru ture in other programs if we wish. Clearly. First. must ontain the array board and the variables emptyBegin and emptyEnd of Se tion 12.5. and to remove elements from the queue.5. The insert method he ks . Se ond. There must be methods to insert an element into the queue.2. as a result the program will be ome easier to read.1 shows the ode.emptyEnd has moved to the onstru tor.

In fa t. manufa turers expressly warn against su h use: often the guarantee about orre t operation given by the manufa turers is onsidered null and void if you as mu h as open the ba kside of the devi e. 14. for example. he/she would like to make a guarantee to you regarding how it will work. The key dieren e is that the ode of queue management: he king for empty.1). you would not. it is unlikely that a fun tion using the Queue stru ture su h as the fun tion main of Figure 14. The net result is that the main program be omes simpler and easier to understand. Likewise. Otherwise it returns true (su ess) and the value is stored in the queue.2.rst if the queue is full. the guarantee will be .3) or Queue (Se tion 14. The situation is very similar to pa kaged devi es sold on the market. be ause their logi is not mixed with taxi dispat hing.2. the designer usually has very lear ideas as to what are proper uses of the stru ture and what are the improper uses. when a professional programmer designs a stru ture for your use. it is expe ted normally that you would only operate the ontrols provided to you on its front panel. put wires inside it and try to onne t it to some other devi e. exa tly as in Se tion 12.5. and for this they will use the provided insert and remove methods.1 will ontain a statement q. in rementation. Likewise for the method remove.14. For example.2. V3 (Se tions 14. The index emptyBegin is in remented. However.5) is designed.emptyBegin=7.6 A ess Control When a stru ture su h as Book (Se tion 14.. If you buy a radio. It is expe ted that users of Queue will only insert and remove elements. and if so returns false (failure).5. is moved to the method insert. The methods in Queue are also easy to understand. just as in Se tion 12.

stru t Queue{ int emptyBegin. emptyBegin = (emptyBegin+1)%QUEUESIZE.insert(value)) out << "Cannot register.\n". Do not distribute 238 #in lude <simple pp> onst int QUEUESIZE=101. return true. // queue is full board[emptyBegin℄ = value. Abhiram Ranade. } bool insert(int value){ if(emptyBegin == emptyEnd) return false.\n".1: Taxi dispat h using Queue . // queue is empty emptyEnd = (emptyEnd+1) % QUEUESIZE. Queue(){ emptyBegin=0. } bool remove(int & item){ if(emptyBegin == (emptyEnd + 1) % QUEUESIZE) return false. } } Figure 14. if (!q. } else if(value == 0){ int item. int value. return true.remove(item)) out << "No taxi available. emptyEnd=QUEUESIZE-1. item = board[emptyEnd℄. else out << "Assigning: " << item << endl. } in >> value. int emptyEnd. while(value >= 0){ if(value > 0){ if(!q. int board[QUEUESIZE℄. main(){ Queue q. in >> value. } }. 2011.

6. Abhiram Ranade.3. Do not distribute 239 valid only if you use the stru ture as des ribed by the designer.1 A ess spe i. This is like the ontra t view of fun tions des ribed in Se tion 9. 14. 2011. It is only stronger: C++ allows the designer to prevent ertain kinds of a esses to the stru ture.

ers You may designate ea h member of a stru ture as either being private. To do this we divide the members in the lass into groups. private: or prote ted: as we want the members in the group to be onsidered. or prote ted. You may use as many groups as you wish. and before ea h group pla e publi :. For example we may de. publi .

} bool insert(int value){. int emptyEnd. In this.... Private members an be a essed only inside the methods of the lass..ne the stru ture queue as: stru t Queue{ private: int emptyBegin. int board[QUEUESIZE℄.. publi : Queue(){. and are not a essible outside the lass de.. all the members following private: until the publi : are said to be private.} bool remove(int & item){.} }.

In other words.6. Thus we would not be able to write a statement su h as q. The members following publi : on the other hand.emptyBegin=7. are onsidered to be a essible by all.nition (but also see Se tion 14.2). in our main program { the ompiler would ag it as an error. they an be used inside the lass de.

the above ensures that outside of the de.nition if needed. In other words. but also outside of it.

as you will see later). insert elements. We will explain prote ted members later. but not look at the data members. we an onstru t an instan e of Queue (use the onstru tor).2 Friends If you make some members of a stru t private.nition. 14.6. and a arefully hosen set of fun tion members publi . or remove elements. then they an only be a essed inside the stru t de. A very ommon idea is to make all data members private (or prote ted.

e. Suppose we want to enable a Queue instan e to be printed. .nition.. i.. out << q. Sometimes this is too restri tive. we would like to write Queue q. .

the output stream and a Queue instan e. Do not distribute 240 As we dis ussed earlier. Abhiram Ranade. We would like the output stream to be the . This fun tion will take two arguments. 2011. we an do this by overloading the fun tion operator<<.

rst argument. Hen e this fun tion annot be ome a member fun tion for Queue. sin e then the queue instan e would have to ome .

Thus we are for ed to write the overloading fun tion outside of the de.rst.

You go ahead and de. whi h is not allowed. C++ allows you to over ome this diÆ ulty. This poses a problem be ause operator<< would need a ess to the private members of Queue.nition of Queue.

In fa t. } return ost. else{ for(int i=(emptyEnd+1) % QUEUESIZE.. the private members of stru ture B an be used inside the de. the line will read friend fun tion-de laration. whi h means that it is allowed to a ess the private members of Queue.) ost << i << ": " << board[i℄ << endl. you put a line in Queue along with the member des riptions as follows: stru t Queue{ .. V3 v){ if(emptyBegin == (emptyEnd + 1) % QUEUESIZE) out << "Queue is empty.. However. friend ostream & operator<< (ostream ost. } This will de lare operator<< to be a friend. In general. This way. Note that the same fun tion an be a friend of several stru tures.\n". } To enable the fun tion operator<< to a ess the private members of Queue. i != emptyBegin. . you provide sele tive a ess. Noti e that you ould have a heived the same ee t by de laring all members to be publi ..ne the operator<< fun tion as you wish. by making a fun tion a friend. that would allow all fun tions a ess. V3 v). you an have one stru ture A be a friend of another stru ture B. i = (i+1) % QUEUESIZE. a essing the private members also. ostream & operator<< (ostream ost.

nition of stru ture A. inside the de. To do this you merely insert the line friend A.

7 Classes A stru ture as we have de. 14.nition of stru ture B.

all members are onsidered publi by default. a member that is not in any group that is pre eded by a spe i.e. i. The small dieren e between the two is as follows. is more ommonly known in C++ as a lass.ned it. In a stru ture. ex ept for a minor dieren e.

all members are onsidered private by default.er is onsidered publi . In a lass. To .

2011. you simply need to use the keyword lass instead of stru t in the de. Do not distribute 241 get the latter behaviour. Abhiram Ranade.

whi h we will onsider in the following hapters.nition. there are a number of other features in lasses/stru tures... It is ustomary to use the term obje t to denote instan es of a lass. In addition to the features onsidered in this hapter. lass Queue{ . }.8 Header and implementation . 14. the most notable of them being inheritan e.

a lass (or stru t) will be developed independently of the program that uses it. Thus we need a proto ol by whi h the ode that de.les Quite often. possibly by a dierent programmer.

nes the lass an be a essed by ode in other .

it is ustomary to organize ea h lass C into two . Following our dis ussion of fun tions.les.

When the implementation is given as a part of the lass de. the bodies of all member fun tions together are said to onstitute an implementation of the lass itself. pp. It is ustomary to say that the body of ea h memberfun tion provides an implementation of the member-fun tion. some important terms. First.h and C. In fa t.les: C.

it is more ustomary to put the de. it is said to be given in-line. However.nition. when lasses are large and developed independently.

nition of a lass C without out the implementation. into the .

h.le C. the so alled header .

The implementation is put into the .le.

3. using some spe ial syntax. and implementations in C. We show this using an example. their de larations an also put in C. If there are any friend fun tions.h. We will show the . Consider our lass V3 of Se tion 14.le C. pp. pp.

h and V3.y. pp for it. and de lare the data members x. Often.z as private. we do not expe t users to . We will make V3 be a lass. as is ustomary.3.les V3. when a ve tor is reated. What we show here is slightly dierent from Se tion 14.

often alled a essor fun tions be ause they a ess the members. The .ddle with individual oordinates. For this we have provided additional member fun tions. users may want to know the values of (but not modify) the omponents. however.

V3 operator*(double t). publi : V3(double p=0. lass V3{ private: double x. z.h for all this would be as follows. double q=0. . V3 operator-(V3 w). V3 operator+(V3 w).le V3. double length(). // a essor fun tions double gety(). y. double getx(). double r=0).

2011. We next show the implementation . friend ostream & operator<<(ostream & ost. Do not distribute }. ostream & operator<<(ostream & ost. V3 v). double getz(). V3 v). 242 Abhiram Ranade.

whi h de.le V3. pp.

nes the member fun tions. A de.

nition of a member fun tion f appearing outside the de laration of a lass C is identi al to the de.

ex ept that the name of the fun tion is spe i.nition had it appeared in-line.

The onstru tor for lass C will appear as C::C. of ourse. The last fun tion in the .ed as C::f.

z). V3 v){ ost << "(" << v.} double V3::getz(){return z. #in lude <simple pp> #in lude "V3. } V3 V3::operator-(V3 w){ return V3(x-w. z-w. } V3 V3::operator*(double t){ return V3(x*t. return ost. y+w.x.} // other fun tions ostream & operator<<(ostream & ost. "<< v.y. z*t).le is the friend fun tion operator<< for the lass V3. } double V3::getx(){return x. y-w. } double V3::length(){ return sqrt(x*x+y*y+z*z).x << ".y.y << ". "<< v.z). z = r.h" V3::V3(double p. } Our . y*t.} double V3::gety(){return y.x. double q. y = q. } // onstru tor // member fun tions V3 V3::operator+(V3 w){ return V3(x+w. double r){ x = p.z << ")". z+w. as is ustomary.

However.le V3. it is a eptable if some of the implementations are pla ed in line in the header . pp ontained implementations of all member fun tions.

Typi ally.le. small member fun tions are left in-line in the header .

le. while the large member fun tions are moved to the implementation .

8.1 Separate ompilation We an now separately ompile the implementation . 14.le.

and produ e. This module.le.o. the obje t module V3. and the header . for the lass V3.

must be given to any programmer that uses the lass V3.le. Suppose a program using V3 is ontained in the .

le user. pp. then it must in lude the .

h.le V3. The program an now be ompiled by spe ifying .

pp V3. Do not distribute s++ user. 2011.o Other sour e/obje t . 243 Abhiram Ranade.

14.les needed for the program must also be mentioned on the ommand line.2 Remarks The general ideas and motivations behind splitting a lass into a header .8. of ourse.

le and an implementation .

In whi hever .le are as for fun tions.

le the lass is used. the header .

le must be in luded. be ause the lass must be de.

ned. The implementation .

le or its obje t module is needed for generating an exe utable. By not exposing the implementation .

without ae ting the user program. we leave open the possibility that the implementation an be hanged.le to the user of the lass. So long as the de.

nition in the header .

The pro ess of de. we an templatize lasses as well. 14.le does not hange. the user program does not have to hange.9 Template lasses Like fun tions.

z. } The template variable T determines the type of ea h omponent x. z = r. } y = q. template<T> lass V3{ private: T x.x. z.y. y+w. T q=0. T r=0){ x = p.} template<T> V3 V3::operator+(V3 w){ return V3(x+w.z).ning a lass template is very similar. V3 operator+(V3 w). Here is a template version of our V3 lass. y. z+w. and is expe ted to be spe i.y. publi : V3(T p=0.

We have only shown 2 member fun tions for brevity. One is de.ed either as float or double.

ned in-line. the other is de.

ned outside the lass de.

Note that you must put the line template<T> before the member fun tion de.nition.

Note that the template de.ned outside as well.

you must spe ify a value for the template variable and aÆx it in angle bra kets to the lass-name. To reate a lass.b. but a s heme to reate a lass. This will reate the lass V3<float> from the template. . as well as de.nition does not reate a lass. To reate a lass of the template with T being float. you simply write: V3<float> a.

Note that the template for a lass must be present in every sour e .ne a. to be variables of type V3<float>. In your programs. you an use V3<float> as a lass name.b.

le that needs to use it. So it is ustomary to pla e it in an appropriate header .

Noti e that the lass is .le.

Indeed.11 Exer ises 1. Thus 14. Line. Write a fun tion whi h returns a ir le having two given points as the endpoints of a diameter. . Point are all names of lasses. the names Turtle.b. 14. Polygon. Do not distribute generated only when an instan e is reated as in the line V3<float> there is no notion of separately ompiling a template.10 Graphi s By now you have probably realized that our graphi s ommands (Chapter 4 and elsewhere) are built using lasses. a. Re tangle. 244 Abhiram Ranade. Assume the de. The ommands to reate reate orresponding obje ts on the anvas were merely orresponding onstru tors. 2011. The various operations we have des ribed on the graphi s obje ts are member fun tions. above.

2.nition of the ir le stru ture given in Se tion 14. De.1.

ne the operator >> for the lass V3. De. When this is exe uted. This should enable you to write in >> v. the user will type in 3 oating point numbers whi h will get pla ed in v. 3. where v is of type V3.

say a bool type.ne a stru ture for representing omplex numbers. Note that this onstru tor annot have just two real arguments { that will lash with the onstru tor taking real and imaginary parts as arguments. In addition to having a onstru tor whi h takes the real and imaginary parts as arguments. whi h if spe i. and returns a omplex number rei = r os + i sin . write a onstru tor whi h will take as arguments r. Add an optional argument.

ed says whether the pre eding two arguments are to be interpreted as real and imaginary parts or as r:. 4. De.

*.operators so that they return the sum.ne a lass for storing polynomials. Write a member fun tion value whi h takes a polynomial and a real number as arguments and evaluates the polynomial at the given real number. Overload the +. produ t and dieren e of polynomials. Assume that all your polynomials will have degree at most 100.. Also de.

and then pro eed to read in the . It should ask for the degree d of the polynomial.ne a member fun tion read whi h reads in a polynomial from the keyboard. he k that d 100.

rst d + 1 oeÆ ients from the keyboard. De.

5. Make sure that you only print d + 1 oeÆ ients if the a tual degree is d. Overload the >>. Carefully de ide whi h members will be private and whi h will be publi .ne a print member fun tion whi h auses the polynomial to be printed. De. << operators so that the polynomial an be read or printed using them.

e. re tangles whose sides are parallel to the axes. i. An axis parallel re tangle an be represented by the oordinates of the diagonally opposite points.ne a stru ture for representing axis parallel re tangles. Write a fun tion that takes a re tangle (axis parallel) as the .

Write a fun tion whi h takes a re tangle .rst argument and a point as the se ond argument. and determines whether the point lies inside the re tangle.

dy and returns a re tangle shifted by dx. 2011. 6.dy in the x and y dire tions respe tively. De. Do not distribute 245 and double values dx. Abhiram Ranade.

pri e.ne a lass for storing information about a book for use in a program dealing with a library. and the identi. author. a library a ession number for the book. The lass should store the name.

ation number of a library patron (if any) who has borrowed the book. This .

eld. patron identi.

Read information about books from a . ation number ould be 0 to indi ate that the book is not borrowed.

When a patron issues/returns a book. Then you should enable patrons to issue and return books.le into an array of book obje ts. the patron identi.

Write fun tions for doing this. ation number of the book should be hanged.g. e. a book that is already re orded as borrowed is not being borrowed without . The fun tions should he k that the operations are valid.

rst being returned. .

Chapter 15 A proje t: osmologi al simulation It ould perhaps be said that the ultimate goal of S ien e is to predi t the future. S ientists seek to dis over s ienti.

And so on. two masses ma . heavenly bodies intera t with ea h other using just Newton's laws of motion and gravitation. For the most part. predi ting what happens to a large system is diÆ ult be ause of the enormous number of omputations involved. And the next instant after that. We will examine one natural idea for doing su h simulations. 246 . However. the law of gravitation states that. As you might re all. Suppose we know the state of the stars in a galaxy at this instant. Indeed many produ ts are built today only after their designs are simulated on a omputer to see how they hold up under in dierent onditions. whi h will still be quite naive as ompared to the ideas used in professional programs. We wil use our graphi s ma hinery to show the simulation on the s reen. simulating a galaxy is rather simple. we understand the physi s of ollisions and of the materials used in a ar well enough to predi t how badly a ar will be damaged if it ollides against a barrier of ertain strength at a ertain velo ity. The term simulation is often used to denote this kind predi tive a tivity. we an very well predi t how they will behave in dierent ir umstan es. laws so that given omplete knowledge of the world at this instant. In this hapter and Chapter ??. We will ode up this idea. Predi ting what will happen to the entire world is still very diÆ ult.1 Mathemati s of Cosmologi al simulation In some sense. partly be ause we do not yet know all laws governing all obje ts in the world. The simulation in this hapter is osmologi al. for many systems of interest. and then examine the aws in that idea. we will build a number of simulations. mb with separated by a distan e d attra t ea h other with a for e of magnitude 1 Gma mb d2 1 We will sti k to the non-relativisti laws for simpli ity. 15. We will then see an improved idea. For example. Can we say where they will be after a million years? Astronomers routinely do simulations to answer su h questions. the laws will enable you to say what ea h obje t will do in the next instant. Even if we knew all the laws.

is that if the interval size is small.3) vi0 = vi + ai We are not given ai expli itly. onsists of a set of heavenly bodies. then we may assume with little error that the average velo ity remains un hanged during the interval for the purpose of al ulating the position at the end of the interval. and will apply in simulating other (more earthly!) physi al phenomenon involving uid ow. the value of f was not really onstant during every interval. We do not know the average velo ities and a elerations. whi h we will refer to as stars for simpli ity. Assuming that the average velo ity is simply the velo ity at the beginning we may write ri0 = ri + vi (15. rb are the ve tors denoting the positions of the masses. Our system. then the a eleration does not hange mu h during it. then. The for e on mass ma is in the dire tion rb ra. vi0 be the values after time . The state of the system will simply be the position and the velo ity (magnitude and dire tion) of the stars. but we have all the data to al ulate it. The net for e is obtained 3 0 0 . Euler's observation also applies to the a eleration: if the interval is small.5 to integrate f (x) = 1=x. but we assumed it is onstant provided the interval is small enough. Suppose we know the initial state. we may write: ri0 = ri + vi vi0 = vi + ai where vi is the average velo ity (ve tor) of the ith parti le during the interval [t . then presumably more omplex laws have to be brought in. Suppose we want to know the values after some time . i. and hen e we may write the for e on mass ma in ve tor form as Gma mb (rb ra ) (15. However. and indeed. and we may write: (15. be ause we know ri. attributed to Euler. t + ℄ and ai is the average a eleration during the interval. the key observation. Do not distribute where G is the gravitational onstant.2) Now. Thus the average a eleration an be assumed to be the a eleration at the beginning. then the distan e between the masses is d = jrb ra j. the ideas used in the simulations are very general. It is worth noting that su h simulations have ontributed a great deal to our understanding of how the universe might have been reated and in general about osmologi al phenomenon. Euler's observation is similar to the idea we used in Se tion 6. stresses and strains.e. Letting ri0 . But a substantial part of the simulation only on erns how the heavenly bodies move under the ee t of the gravitational for e. If ra .6. ir uits and so on. we an easily al ulate the new position ri0 for ea h parti le. it is not easy to ompute these quantities. The ve tor form of this is also important.1) jrb raj If planets ollide. 247 Abhiram Ranade. 2011. vi. for ea h star i we know its initial position ri and velo ity vi (both ve tors). The a eleration of the i th star is simply the net for e on it divided by its mass mi. Also. whi h might have to deal with how their hemi al onstituents rea t.

vi. 2011. However. The rule to ompute vi0 an also be re. Perhaps you have studied a formula in kinemati s for the ase of uniform a eleration of a parti le: s = ut + at =2. but the approximation is likely to be good if is small. vi for all i. and we want the state at time t = T . 2.4) mi j 6 i jrj ri j 3 = We have des ribed above a pro edure by whi h we an get the state of all parti les at time t + given their state at time t. Then we use the state omputed for time as the input to our basi pro edure to get the state for time 2. It turns out that this method an be extremely slow. mi for all i. vi. with the a eleration. For step s = 1 to T=: (a) Cal ulate ri0 a ording to equation (15. respe tively. Read in the state at time 0. but you should be able to write it quite easily. and so on. vi = vi0 for all i 4. Pi king a good is tri ky. Suppose now that we know the state of our system at time t = 0. ( ) Cal ulate vi0 a ording to equation (15. T .e. Our answers are approximate. in whi h s is the distan e overed. initial velo ity and time being ai. a the a eleration. We will not present the ode for this algorithm. u the initial velo ity.4) for all i. But we know how to al ulate the for e exerted by one star on another. Thus we may write: F X Gmj (rj ri ) ai = i = (15. Read in . we use our basi pro edure to al ulate the state at time given the state at time 0. One su h variation employs the following rule to ompute ri0 ri0 = ri + vi + ai =2 (15. (b) Cal ulate ai a ording to equation (15.3). be ause the stepsize must be taken very small to ensure that the errors are small. To do this. we merely run T= steps of our basi pro edure! In parti ular. there are many variations on the method whi h have better running time and high a ura y. we will assume that we are somehow given a value for it.5) where ai is to be al ulated as before. This may be written as: 1. i. You may re ognize this form. and t the time. 3. (d) Set ri = ri0 . 248 Abhiram Ranade. Do not distribute by adding up the gravitational for e on star i due to all other stars j 6= i. the values ri. for all i. end for 5.2) for all i. Print ri. Our formula is really the same.

ned as follows. a + a0 vi0 = vi + i i (15.6) 2 2 2 .

the story does not end here. ( ) Cal ulate a0i a ording to equation (15. 3.6 are said to onstitute the Leapfrog method of al ulating the new state. (d) Cal ulate vi0 a ording to equation (15. Abhiram Ranade.1 is based on this.e. the values ri.3). using equation 15.4. 2.15. for all i. Do not distribute 249 1. end for 5. Of ourse. It turns out that the Leapfrog method does indeed give more a urate results for the same value of as ompared to the simpler rules in Equations (15. for all i. . The algorithm in Figure 15.6).5 and 15. State of the art programs for harting the evolution of stars use even more re.2.1: Basi Leapfrog in whi h a0i is the a eleration al ulated at the new positions of the stars. and at the end is a0i. vi for all i. vi.1 is ineÆ ient: the value a0i al ulated at the end of an iteration of the loop is re al ulated at the beginning of the next iteration. This is what the above rule uses. For step s = 1 to T=: (a) Cal ulate ai for all i using equation 15. 4. i. The a eleration at the beginning of the interval is ai.4 but with ri0 instead of ri. Equations 15. You will note that the algorithm in Figure 15. i. Update ri = ri0 for all i. We will avoid this in the ode we des ribe later. Figure 15. T . Update vi = vi0 .e. mi for all i. It is not hard to understand the intuition behind this formula. Print ri. The a a0 average of these. (b) Cal ulate ri0 a ording to equation (15. Read in the state at time 0.4) for all i. Read in . 2011. is likely to be a better estimate of the a eleration during the interval rather than simply ai .5) for all i.

2 Overview of the program Let us . These are outside the s ope of this book.ned methods. i+ i 2 15.

rst learly write down the spe i.

We will also be given a number T . Our goal will be to . Our input will be positions and velo ities of a ertain set of stars at time 0. ations.

We are also asked to show the traje tories tra ed by the stars between time 0 and time T .nd the positions and velo ities of the stars at time T . The .

orresponding to ea h spatial dimension. of ourse. A star has several attributes. velo ities. The traje tory of a star is also to be shown on the s reen. and its mass.8 to represent positions. the velo ity and position both have 3 omponents. we an use our V3 lass of Se tion 14. . However. and a elerations. The mass is simply a oating point number.rst question in writing the program is of ourse how to represent the dierent entities in the program. its velo ity and position. The main entity in the program is a star. Clearly.

So we rearrange the ode slightly.6). har* argv[℄){ initCanvas("Star satellite system". For step s = 1 to T=: (a) Cal ulate a0i a ording to equation (15. 15.1. be ome statements 5( ).4) for all i.1000. Cal ulate ai for all i using equation 15. we should move the Point asso iated with the star. 6. However. 3. 4. and they be ome statements 3.5. 3(b) out of the loop of Figure 15. i.4.1. i. Update ri = ri0 for all i. when s = 1. as shown in Figure 15. When we ompute the new position of a star. ( ) Update ai = a0i for all i. 2011. As we mentioned in the previous se tion.e. int main(int arg . we do need to al ulate ai be ause there is no previous iteration.2: Final Leapfrog algorithm So we probably should asso iate a graphi s obje t. . for all i. 5(d). It will advan e this variable in small steps to rea h the given duration T .2. Note that ai of the next iteration is the a0i of the previous. Abhiram Ranade.2. say a Point. and they also get added to the end of the loop. Update ri = ri0 for all i. the value a0i al ulated at the end of the sth iteration is the same as the value ai al ulated at the beginning of the s + 1th iteration. 5. and all appropriate methods on the stars to update their positions and velo ities.-1. 4 in Figure 15. for all i.2. vi. Read in .50. so in statement 5( ) we did not re al ulate ai .e. but merely set ai = a0i. (d) Cal ulate ri0 a ording to equation (15.2. mi for all i. Figure 15. the values ri. it will al ulate the for es. in the manner of Figure 6. We pulled up statements 3(a). Print ri. 2.2.15. vi for all i. Update vi = vi0 . Cal ulate ri0 a ording to equation (15. end for 7. As it advan es time. (b) Cal ulate vi0 a ording to equation (15. Read in the state at time 0.1 Main Program The main program will reate the stars. ifstream simDatafile(argv[1℄).6). Figure 15.5) for all i. Do not distribute 250 1.1000). It will maintain a variable to keep tra k of the elapsed time.5) for all i. with ea h star.2 is really a slight rearrangement of the ode in Figure 15. T . The star lass will need a onstru tor and some methods to implement the position and velo ity updates as per Equations (15.

delta. arstep(n. The program reates the anvas to show the orbits. t<T. float T. } wait(5). simDatafile >> T >> delta. Star stars[n℄. simDatafile >> n.stars. t+=delta){ avrstep(n. 2011. Do not distribute 251 int n. delta). delta). } for(float t=0. n. setup_star_data(simDatafile. then opens the . onst float star_radius_for_graphi s = 15. Abhiram Ranade.stars. star_radius_for_graphi s). stars.

le ontaining the data about the simulation. It expe ts the .

lename to be spe i.

ed as a ommand line argument.e. and delta the time step duration. T. the value from the . the time duration of the simulation. It reads n. the number of stars. i.

y. The avrstep fun tion is identi al. } assert(file). stars. it al ulates the for es on ea h star due to other stars. The for e on ea h star is passed as an argument to the arstep method of ea h star. i<n.vy.le given. using the fun tion al ulate net for e.4 of Figure 15. for es). i++) stars[i℄.z). The task of al ulating for es is fairly simple as you would expe t. Next. . i++){ file >> mass >> x >> y >> z >> vx >> vy >> vz.init(mass. for(int i=0. void setup_star_data(ifstream & file. vz. Then. V3(x.vz). the fun tion read star data reads the data about the stars into the array stars of lass Star. // qui k he k that input was valid } Then it alls the fun tion arstep orresponding to steps 3. within the loop. Star stars[℄. x.arStep(delta. V3(vx. ex ept that it alls the avrstep method for ea h star. float delta){ V3 for es[n℄. for es[i℄). i<n. void arstep(int n. z.2. vy. The fun tion arstep is as follows. stars[i℄. vx. orresponding to steps 5(a){5(d). for(int i=0. } As you an see.y. It pla es the data read into ea h star obje t. al ulate_net_for e(n. int n. radius). Star stars[℄. float radius){ float mass. the fun tion avrstep is alled.

Noti e how the V3 lass makes it easy to write this fun tion. and subtra t it from the total for e on star j . Star stars[℄. These fun tions an be pla ed in a . double dist = distve . for es[j℄ = for es[j℄ . i++){ for(int j=i+1.getMass()*stars[j℄. and add it to the total for e on star i. for es[i℄ = for es[i℄ + f.f. double fmag = stars[i℄. // for e on star i Sin e the for e due to star i on star j has the same magnitude as the for e due to star j on star i.length(). } } } V3 f(distve *(fmag/dist)). i<n.stars[i℄. j++){ V3 distve = stars[j℄. So we al ulate the for e just on e.getMass()/(dist*dist).getr() . Do not distribute 252 void al ulate_net_for e(int n. V3 for es[℄){ for(int i=0. 2011. but opposite dire tion. j<n. i<n-1. i++) for es[i℄=V3(0.0). for(int i=0.getr(). Abhiram Ranade.

pp.3 The lass Star The header .le. 15. main.

// position. V3 getr(){return r. in the implementation . float getMass(){ return mass. V3 r.y oordinates of the position (stored in member r) will be used as the position of ea h body on the s reen. The data member visual.} }. publi : Star(){}. you may onsider that we are viewing the osmologi al system in the z dire tion. V3 position.h is as follows.v. lass Star { private: Point visual. will be used for produ ing the graphi al animation. void avrStep(float dT.} void init(float m. V3 velo ity. so that the orbit will be tra ed on the s reen.a. velo ity and previous a eleration values. The x. of lass Point.le star. V3 f). void arStep(float dT. The member visual will be made to put down its pen. as you will see in the member fun tion init.y oordinates are important. V3 f). so that only the x. float radius). float mass.

pp below. .le star.

} void Star::arStep(float dT.h" #in lude "star.setFill(true).gety()).setFillColor(COLOR("red")). V3 v1. visual.0).penDown(). a = adash.Position(r. V3 f){ a = f*(1/mass). outside loop void Star::avrStep(float dT.init(radius. visual.getx(). r = r1.show(). V3 r1. V3 f){ V3 adash = f*(1/mass). Do not distribute #in lude "V3.getx().d.move(d.move(d.4 Compiling and exe ution The . } // basi loop step // update anvas // update anvas It should be self explanatory.gety()). r = r + d.gety())).d.h" void Star::init(float m.Position(0. visual. visual. r = r + d. 15.getx().r. 253 Abhiram Ranade. V3 d = v*dT + a*dT*(dT/2). float radius){ mass = m. v = v+(a+adash)*(dT/2). 2011. visual. visual. visual. v=v1. } // first step. V3 d = v*dT + a*dT*(dT/2).

To exe ute the program we need a . pp and star. pp star.o where we assume that V3. pp V3.les an be ompiled by giving s++ main.h and V3. pp.o from Se tion 14.8 are in the same dire tory as main.

le ontaining the data for stars. A sample .

466203685 0. 3 3000 10 100 497.le 3stars.00436 375.43236573 0 .691247 0 0.txt is as follows.

254 Abhiram Ranade.3: 3 stars in a . 2011. Do not distribute Figure 15.

308753 0 0.txt The stars will tra e an interesting . The initial positions and velo ities of the stars are given as above. with = 10.86473146 100 302.932407370 -0. You an simulate this system by typing: . Note that they have been arefully al ulated.466203685 0.out 3stars.43236573 0 0 This is meant to simulate a 3 star system for 1000 steps.gure of 8 orbit 100 400 400 0 -0./a.99564 424.

gure of 8 orbit on whi h they will hase ea h other. Our program also illustrates two important program design ideas. The general notion of simulating systems of interest is very important. 15. Clearly. note that we did not write one long main program: we identi. But as we noted. the governing laws an be applied in more or less sophisti ated ways. as we saw. and will also give even more sophisti ated ideas than what we presented. The stars have their pen down. and the governing laws. there were many ve tor like entities in the problem: so it was useful to build the lass V3 as well. Texts on numeri al analysis will indi ate how the error an be estimated.5 Con luding Remarks There are a number of noteworthy ideas presented in this hapter. However. Given the initial state of a system. First is the idea of building lasses to represent the entities important in the program. leading to more or less error in the result.3 gives a snapshot. we an in prin iple determine the next states. Figure 15. Finally. and hen e the orbits tra ed are also visible. the important entities in our program were the stars: so we built a lass to represent them.

a small te hni al point should also be noted. For this. This idiom will ome in useful whenever you need arrays of obje ts in your programs. We needed to reate an array of Star obje ts. Finally.ed important steps in the main program and used fun tions to implement those steps. The fun tions. ea h obje t an be initialised only using the onstru tor whi h takes no arguments. Hen e we had a Star() onstru tor. more learly indi ated the omputational stru ture of our algorithm. . when an array of obje ts is reated. even if used just on e. a ommon idiom is to provide an init member fun tion. We all the init fun tion on ea h obje t in the array and set its ontents. as we did.1.3. But this leaves open the question of how to pla e data in ea h obje t. As we indi ated in Se tion 14.

or diverges mu h less. they should implement a member fun tion li kedP whi h takes an int denoting the position of a li k. For small enough velo ities. Simulate the motion assuming there is no gravity. Build the osmologi al simulation using both the methods given in the text. Consider a sequen e of ars travelling down a single lane road. whi h is learly erroneous. Consider an elasti string of length L tied at both ends. i. Further assume that the driver is aware of this distan e. 3. For the same stepsize. Use it to simulate a system onsisting of a planet orbiting a star. the springs on either side of the mass will stret h equally. suppose that the ars have the same maximum speed V . onne ted together by springs of length L=n + 1. Of ourse. as obtained from getCli k(). You will observe. however. if the string is stret hed by distan e x.g.e. Suppose it onsists of n equal weights. you should be able to observe that the leapfrog orbit does not diverge. Do not distribute 15. the leading ar in the onvoy brakes so that it omes to a halt at the signal. be ause of an a ident). and speeds up if the distan e in reases. Suppose ea h ar attempts to ensure that it an ome to a halt even if the ar ahead of it were to stop instantaneously (e. whi h an be li ked. the drivers do not rea t immediately. When a signal turns red. and a eleration a and de eleration d. the orbit will keep diverging for any stepsize. Now suppose the mass is released. 2011. 4. Clearly. 2. a tension kx is produ ed. What other member fun tions might be useful for buttons? . Also. Note though that usually it is very easy to see if the ar ahead is slowing down. Clearly. Suppose ea h spring has Hooke's onstant k. you should be able to onstru t buttons at whatever positions on the s reen. and slows down if the distan e ahead redu es. be ause the tail red light omes on. the planet will travel around the star for both methods.6 Exer ises 255 1. with whatever text on them. In orporate su h details into your simulation. Suppose the string is at rest after this. Show an animation of the simulation using our graphi s ommands. if gravity is ignored. Suppose one of the masses is moved to some new position. say a re tangle. but only till the speed rea hes V . that for Euler's method. Build a simulation of a onvoy of ars whi h travels along the road on whi h there are signals present. Abhiram Ranade. but have some response time. and determine whether the li k position is inside the button. Constru t a lass Button whi h an be used to reate an on-s reen button. In a simplisti model.

whi h would have to be a member in the lass whi h would represent the polynomial. On the other. How mu h memory do you reserve for it? In Exer ise 14.b } out << . In general you may not know the degree of the polynomial that you will en ounter. having an upper limit of 100 on the degree is unsatisfa tory. we would like to be able to represent polynomials using just about as mu h memory as the degree of the polynomial. we would be working with all the 101 oeÆ ients.read(). main(){ Poly a. In other words. Ideally. So using an array of 101 elements in ea h polynomial variable is a wastage of memory. a.b.4 you were asked to build a lass for representing polynomials. // Value of polynomial (x) when x=35.read().value(35) << endl. In Exer ise 14. Clearly this an be very ineÆ ient. // read another. there is also an issue of eÆ ien y: when we ompute a*b. be ause a lass/stru ture is required to have a . Finally. Su h a lass Poly an be built using what you already know. = a*b. This annot be done dire tly using lasses/stru tures. // is produ t of a.Chapter 16 Representing variable length entities We ontinue with the idea of building lasses to represent entities that we might want in our programs. Thus the polynomial ould have as many as 101 oeÆ ients.4 it was given that the degree of the polynomials would be at most 100. . But there is a problem. even if our polynomials have small degrees. of possibly different degree. On the one hand. The idea was that it would enable us to write a program like the following. the implementation that was expe ted as an answer to Exer ise 14. These would have to be stored in an array of length 101. it is possible that many polynomials that arise in our program have a very small degree. // read a polynomial b.4 is not really satisfa tory for general use.

The most onvenient way of representing entities whose size is not known when we write the program is to use the so alled heap memory allo ation. or whose sizes may even vary 256 . whi h will use memory eÆ iently. we will be able to onstru t a data type to represent polynomials. This is also referred to as dynami memory allo ation.xed size. Using this heap memory. In general the heap memory will be useful in building representations for entities whose sizes may not be known at the time of writing the program.

This region is alled the heap memory. Su h variables are present only for the duration in whi h the orresponding fun tion is exe uting. You may assume that a ertain region of memory is reserved for this purpose. or in other words s bytes of memory. Thus. 16. You an request memory from the heap by using the operator new. 2011. Suppose T is a data type su h that ea h variable of type T requires s bytes of storage. to be allo ated in the heap. However. and the expression itself evaluates to the address of the allo ated variable. you must save the address { this you an do typi ally by storing it in a variable of type pointer to T. a C++ program an also be given memory outside of a tivation frames.1 The Heap Memory So far. we have been onsidering variables that have been allo ated in the a tivation frame of some fun tion or another. Do not distribute over time. or just the heap. for the most part. 257 Abhiram Ranade. Then the expression 1 new T auses a variable of type T. To use this allo ated variable. We will see more examples of su h entities later. for the Book type as de.

1. The . p = new Book.ned in Se tion 14. we ould write: Book *p.

00. Other than this. to set the pri e and a ession number respe tively. Thus we ould write q[i℄ where i must be between 0 and n (ex lusive). The se ond statement requests allo ation of memory from the heap for storing a Book variable. if T is a type then we may write T *q = new T[n℄.3. there are the global variables. or a lass. The se ond form of the new operator allows us to allo ate an array in the heap. The memory allo ated an be used by dereferen ing the pointer p. 1 . We ould of ourse have done this in a single statement if we wish.rst statement de lares p to be of type pointer to Book.. They have to be essentially allo ated before the program begins exe ution. whi h will allo ate memory in the heap for storing an array of n elements of type T. and hen e are not interesting for the purpose of this dis ussion. p->a essionno = 12345.3. by writing Book *p = new Book. As again.e. and the address of the allo ated array would be pla ed in q. Note that T ould be a fundamental data type. i. If it is a lass. ea h obje t T[i℄ would be onstru ted by alling the onstru tor whi h does not take any arguments. we may write p->pri e = 335. You must ensure that su h a onstru tor is available. We an a ess elements of the array starting at q by using the [℄ operator as dis ussed in Se tion 12. The address of the allo ated memory is pla ed in p.

Assuming p pointed to memory allo ated as above. Thus. we might write: delete p.e. i. i. We an free memory. There is some bookkeeping needed to be done so that subsequently the same memory is not allo ated for another request. return it ba k to the heap by using the operator delete. until we expli itly free the memory. So for q as de.e. 2011. Do not distribute 258 Note that allo ating memory in this manner is a somewhat involved operation. somewhere it would be noted that the memory starting at p is now free and may be allo ated for future requests. would ause the memory to be returned ba k. Abhiram Ranade. The delete[℄ operator is used if an array was allo ated. delete p.

This is te hni ally alled a memory leak. By this we mean the set of (internal) fun tions and asso iated data C++ maintains to manage heap memory. and a pointer to the array allo ated on the heap. and there is no other opy. the rule is more stringent: a variable is destroyed as soon as ontrol leaves the blo k in whi h the variable is reated. We used the phrase allo ator above. so to say) when you ask for memory using the new operator and release memory using the delete operator.1. then we an no longer a ess the memory area whi h has been given to us. the allo ator might have allo ated that memory for another request. They are a essible only through a pointer! So it is vital that we do not overwrite the pointer ontaining the address of a variable allo ated in the heap. These are the fun tions that get alled (behind the s enes. Variables reated in the heap are dierent.ned earlier. 16. In fa t.1 Lifetime and a essibility We have said earlier that if a variable is reated in the a tivation frame. i. It does not belong to us! Someone else might have moved in there. then it is destroyed as soon as the ontrol exits from the on erned fun tion. we must instead return it using the delete operator and re y le! 16. We must not let memory leak. Note that on e we exe ute delete (or delete[℄) it is in orre t to a ess the orresponding address. The se ond point on erns how the variables on the heap are a essed. we may write: delete[℄ q. . Exiting blo ks. it is almost akin to entering a house we have sold just be ause we know its address and perhaps have a key to it.e. The lass whi h will represent the polynomial will just ontain data members whi h hold the degree of the polynomial. The memory area has now be ome ompletely useless. or returning from fun tions does not ause them to be destroyed: they an only be destroyed by exe uting the delete operations. The key idea is that the oeÆ ients will be stored in an array whi h we will allo ate on the heap. unless we have another opy of it.2 A naive solution We now show how to use heap allo ation for representing polynomials. If we do overwrite a pointer ontaining the address of a heap variable.

For simpli ity. float value(float x). i++) in >> oeff[i℄. i<=degree. the . oeff = new float[degree+1℄. in >> degree. 2011. Here is the implementation of the member fun tion read. } We will see how this exe utes. value and operator*. When the main program exe utes. 259 Abhiram Ranade. void read(). for(int i=0. }. float * oeff. out << "Give oeffi ients from low to high: ". void Poly::read(){ out << "Give the degree of the polynomial: ". we have only de lared the member fun tions read. Do not distribute stru t Poly{ int degree. and some snapshots of this appear in Figure 16.1. Poly operator*(Poly b).

read() is alled. the names degree and oeff will refer to a.degree and a. In the se ond line. The . The variable a is an impli it referen e parameter to the all. in the a tivation frame of main(). when the all exe utes.b. This auses an a tivation frame to be reated for the all. a. oeff respe tively.rst step auses the allo ation of spa e for variables a. In other words.

rst statement of read prompts the user with the .

ontinue to remain allo ated. In the third statement of read. nothing is opied ba k. the memory allo ation an be done only then. and the value of a. the degree be omes known only at the time of reading. Thus oeff will get the value 24000. oeff ontains the address 24000 in the heap. Suppose for example that the array is allo ated starting at address 24000. we read in 3 oeÆ ients into the array. Observe that the heap memory has served our requirements beautifully. we have used only as mu h memory from the heap as was needed to store the oeÆ ients of the polynomial. Suppose the user types in 2. The addresses 24000 through 24011 whi h were allo ated. At this point. 30. sin e we must read the polynomial from the keyboard. Control returns to the main program and the a tivation frame of a. 5. the degree is then read into degree. oeff. Thus. the value 24000 will in fa t be stored in a. the fun tion a. nothing happens to the heap be ause of returning from read.read is destroyed. Suppose the user wants to spe ify the polynomial 5x + 30x + 6. Subsequently. 30. However. Further.read returns. we also want the entire reading pro ess to be expressed 2 . First. a oat array of size 3 (be ause degree+1 is 3) will be allo ated to us from the heap memory. so the user will type in 6. oeff. These lo ations ontinue to hold the oeÆ ients 6.rst out statement. This gets stored in a. But for onvenien e.1(a). At this stage the state of the memory used by the program would be as shown in Figure 16. Sin e the return type is void. 5. Sin e oeff refers to a.degree whi h is what degree in the member fun tion read refers to for this all.

.read() a.degree : b.read() 24004 a.. oeff : Heap memory Address Content 24000 24001 6 24002 24003 24004 24005 30 24006 24007 24008 24009 5 24010 24011 24012 . oeff : . 260 Abhiram Ranade. . oeff : 24000 oeff is a. ...degree a.degree : .. oeff : 24000 exists 30 24006 b. . oeff : 24008 .degree : 2 degree is a. .degree : 24009 .. oeff b. Do not distribute AF of main() AF of a. (a) Before returning from readpoly Heap memory Address Content 24000 24001 6 24002 24003 AF of main() AF of a. 2011. (b) After assignment to a Figure 16.degree : 2 No longer 24005 a.1: Snapshot at the end of readpoly and after return . oeff : 5 24010 24011 24012 .degree : 24007 b.

2011. Do not distribute 261 as a fun tion. If we did not have the heap memory. Thus the memory for storing the polynomial must be allo ated inside the fun tion whi h reads the polynomial. But then the a tivation frame vanishes on e the fun tion exe ution . Abhiram Ranade. the fun tion an allo ate memory only inside its a tivation frame.

This in turn means that the fun tion annot allo ate any memory whi h an be used in the main program! With the heap memory. this problem is solved. and then return. In this a tivation frame b will be the impli it parameter. the memory allo ated on the heap ontinues to remain allo ated. whi h would really be b.degree.nishes. Note that the heap allo ator would realize that the . Suppose this time the user gives 1. Let us ontinue with the exe ution of the program. This will ause an a tivation frame to be again reated for it. Even after returning. the starting point of this would be returned. This would ause a request for a 2 word array to be allo ated. Again the user will be asked to give the degree. The reading fun tion an allo ate memory on the heap.read will be alled. and an be used in the main program. Next b. In response. This would be stored in degree.

4 to represent the polynomial 4x + 3.rst 3 words have been allo ated. Thus 24012 would be returned whi h would be stored in b. These oeÆ ients would now be stored at addresses 24012 and 24016. Suppose the user gives 3. oeff.degree and b. The algorithm of the fun tion is from the . Though nothing would be opied ba k as a result of the all. and hen e would return the next possible starting address from whi h a 2 word array an be stored. we give it below.read() would return. After that the all b. After this the program would ask the user to give the oeÆ ients. We have not given this fun tion. Next there would be a all to the member operator* to evaluate the expression a*b. b. oe would be set to 1 and 24012 respe tively.

for(int j=0. j++) for(int k=0. Thus.degree and op2.rst fun tion in Se tion 12.degree = degree + op2.degree and a.degree and b. the names degree and oeff would refer to a. oeff = new float[prod. prod.degree+1℄.7. operator* would be alled with a as the impli it argument. return prod. and b as the referen e argument op2. To evaluate the expression a*b. oeff[i℄ = 0. inside the body. oeff[k℄. } for(int i=0. 2 . Sin e the parameter op2 is also a referen e parameter . oeff will refer to b. i<prod. This would not hange the exe ution. k<op2. k++) prod.degree+1. With all by value. Poly Poly::operator*(poly onst &op2) onst { // implements op1*op2 where op1 is the impli it argument poly prod. When the exe ution starts. j<degree+1.degree. the value of b would be opied into op2. i++) prod. the stru ture prod will be reated for returning the 2 We ould have used all by value also.degree+1. oeff respe tively. prod. oeff[j+k℄ += oeff[j℄ * op2. oeff respe tively. the names op2.

2011. Abhiram Ranade. whi h is what is . The degree of the produ t is the sum of the degrees of the multipli ands. Do not distribute 262 result.

and the resulting oeÆ ients stored in the memory region 24020 through 24035. this requires an array of size 1 more than the degree.1.b would be 2. oeff would thus be 24020. oeff array of 4 words would be allo ated on the heap. So a prod. When we exe ute this fun tion. Next we allo ate heap spa e to store the oeÆ ients of the produ e. we use the algorithm from Se tion 12. When the fun tion . sin e the addresses until 24019 have been already allo ated to store the oeÆ ients of a and b.degree would be ome 3. Finally. The heap memory allo ator would assign the area 24020 through 24035.rst omputed in the ode above.7 to determine the oeÆ ients. the degree of a. Hen e prod. The value of prod. The produ t would then be omputed.

nishes exe ution. After this the exe ution of the main program would ome to the statement out << . However. Thus we will have the values 3 and 24020 respe tively in . a Poly lass an be useful in many programs.value(35) << endl. In fa t. and use it wherever we need.degree and . Its value would be stored in . oeff. We need to know the value of the polynomial in onsidered as a fun tion of x. } return result. power=1. The implementation of the lass Poly as given above is learly adequate for running the main program given at the beginning of the hapter. i<degree+1. The implementation an also be extended to over other operations su h as polynomial addition. } This will indeed evaluate what we wish. if it is written well. it should even be given to other users. Ideally. we should write it on e. for(int i=0. i++){ result += oeff[i℄*power.2. at x=35.1 Memory leaks Here is a simple example in whi h we might think that our Poly lass will work . float Poly::value(float x){ float result = 0. Is our lass (assuming other useful fun tions for polynomial addition and so on are implemented) good enough for this purpose? 16.. This fun tion is easily written as follows. the stru ture prod will be returned. power *= x.

In this example.ne. the user is . but a tually doesnt.

and the pro ess repeats if the user wants it to. do{ . and a value at whi h to evaluate the polynomial. main(){ Poly a.rst asked to give a polynomial. The polynomial is evaluated at that value. har response. float x.

The key point to note is that the heap memory is .read(). in >> response. out << "Give value of x where to evaluate: ". } while(response == 'y'). Abhiram Ranade. out << "Type y to ontinue: ". in >> x. out << "Value is: "<< a. 2011. Do not distribute } 263 a.value(x) << endl.

At any point in time. we get memory allo ated from the heap. This is ironi . all the memory in the heap will be given to us. the above program runs out of memory even if the user only gives .nite. be ause of two reasons: 1. Everytime we exe ute a. On the other hand. Thus if the user always gives polynomials of small degree. The previous polynomials an be safely forgotten. and eventually our request for new memory will be unsu essful. we are on erned with only one polynomial: the last one typed in by the user. So if our program runs long enough. say at most some k.read(). We do not exe ute any delete operation in our program. then we should only require k +1 words of heap memory at any time to store the oeÆ ients.

On e we start returning memory. a. Everytime memory was given. So at the end of the loop body. Our program an no longer use the memory. the program no longer has any pointers to the memory given to it earlier. It is of ourse easy to avoid this problem. This should be inserted at the end of the body of our loop. but it does not have any re ord of it. in ea h iteration. This is an important issue when using heap memory. But for this to happen. oeff. we have no danger of running out of heap memory! The heap allo ator will give us ba k the memory we returned { it will re y le. we must remember and plan to return memory. However. It will ause the memory we got at the beginning of the iteration to be returned ba k to the allo ator at the end.. as a result. oeff. oeff is overwritten. 16. although as far as the allo ator is on erned. we should . We know that the polynomial we read in one iteration is not needed in the next.2 Dangling Pointers So it might seem that whenever we are about to exe ute a statement su h as ptr = new . it is in possession of our program! This is a lassi ase of a memory leak. its address was pla ed in a. Our program has been given a lot of memory.rst degree polynomials (k = 2) in every request! 2. we an safely return the memory used to store the polynomial by exe uting an additional statement: delete[℄ a..2.

this idea does not always work.rst release the memory that ptr points to by exe uting a delete operation. Consider the following ode fragment in whi h we ould onsider using this rule. Unfortunately. .

e. We know that a.b b = a.degree and b. the polynomial 5x + 30 + 6 is read into a... Unfortunately this leads to disaster! Suppose that this ode exe utes in the manner of Figure 16.1. So following the idea of the previous se tion.read() in statement (iii) will a quire new memory using the pointer a. oeff. by exe uting delete[℄ a. // statement (i) . oeff. // some statements that do not hange a.b. // Statement (iii) The all a. Now both a and b represent the same polynomial 5x + 3x + 6.. So far everything is . otherwise we would not have written b = a. oeff get opied to b.. This is of ourse what we wanted.. a.b a. oeff.read(). i. // Statement (ii) . Do not distribute Poly a. 264 Abhiram Ranade. 2011. When statement (ii) exe utes. a. and a.degree and a. perhaps we should release that memory. oeff gets the value 24000 in statement (i). // some statements that do not hange a. just before statement (iii). oeff indeed points to memory that was given to us in statement (i).read().

This ould be onsidered to be the solution used in the C language. your own program might store something in that memory. oeff points to memory whi h at present is not allo ated to our program. oeff[0℄. but determining when to return it ba k is tri ky. This problem is te hni ally alled the dangling pointer problem. be ause our program still needs this memory. This an produ e unpredi table results. However. oeff is 24000. this statement auses the memory starting at 24000 to be returned ba k to the allo ator. 2 2 3 16. This hore an be handled in various ways. you are referen ing memory that is not yours. never mind that it was given to us earlier. Sin e the value of a. Then suppose we exe ute delete[℄ a. Suppose immediately following statement (iii) you ask for new memory. A quiring memory from the heap is easy. and indeed memory leaks and dangling pointers are an important sour e of errors in C programs. be ause of variable b. The programmer will surely know when the memory is not needed.ne. it is an added programming hore. If you dereferen e su h pointers. 3 x x .3 Solutions One point to be noted from the above dis ussion is that when you use memory on the heap. Thus it should not be returned. and an return it. and in any ase. the pointer b. After the exe ution of statement (ii). destroying the polynomial 5 2 + 30 + 6 whi h was supposed to be ontained in b. But this is an error. The oeÆ ients of the polynomial represented by b are stored starting at 24000. In this ase. whi h we inserted just before statement (iii). say by writing b. programming experien e shows that it is quite diÆ ult to orre tly determine when to return memory. It is possible that the allo ator will give you the memory starting at 24000. oeff. you need to manage it. The simplest option is to leave the job of returning memory to ea h programmer. Su h pointers are said to dangle.

do not return that memory ba k to the heap yet! Does this mean we should ount how many pointers there are to ea h region of the heap that gets allo ated to us? Sophisti ated heap management strategies a tually do this. here is the new de. We will state the basi rules we will use to manage the heap so that neither does memory leak nor do any pointers dangle. we an in fa t hide the heap management a tions inside the implementation of the data type (the stru ture Poly in the present ase). This is be ause we know that if ptr is not NULL it must point to a heap variable. A number of approa hes have been designed. C++ ontains a standard template library (STL) whi h ontains many data stru tures whi h you an use. Do not distribute 265 It is more interesting. The basi idea is: Distin t-pointer rule: Ensure that every pointer points to a distin t heap variable. and no other pointer will point to the heap variable. oeff after statement (ii) of the previous example). of ourse. be ause of the distin t pointer rule. to see if there an be a systemati approa h to managing heap memory. we an avoid all the pitfalls mentioned in the previous se tion! Based on these ideas. and one of the pointers is about to be overwritten. whose implementation already in ludes the approa h of the next se tion. In parti ular. Just by doing that. We will also show how the management a tions an be written into the fun tion members of the Poly stru ture.4 A simple safe solution Perhaps the main rule for returning memory ba k to the heap should be: Last-pointer rule: Return memory ba k to the heap just before you are about to destroy the last pointer you have to it. 2011. based on simple and elaborate ideas. Thus the user of the data type an write programs not even realizing that the heap memory is being arefully managed behind the s enes! In the next se tion. 16. Abhiram Ranade. So this is the key to the implementation we dis uss next: we simply try to adhere to the last pointer rule and the distin t pointer rule. Not only that. we request you to study the next se tion. In the next hapter we will show how to build lasses su h as Poly using STL lasses. if you feel that you will yourself want to develop lasses su h as those in STL. or if you are urious about heap management strategies. But it requires rather elaborate programming. This is in fa t possible. More ommonly a simple approa h is used. we present one su h approa h. if there are two pointers pointing to the same region of memory (su h as a. would not even know that the heap was being managed. The distin t pointer rule makes it very easy to apply the last pointer rule: whenever we are about to hange the value of a pointer ptr. So you may in fa t hoose to skip the next se tion and go dire tly to the next hapter. users of the Poly lass will not have to worry about managing the heap. oeff and b. As we said. However. but no sooner. or is NULL. or in general lasses that will manage heap memory. we release the memory that it points to (provided it is not NULL).

We dis uss the implementation of ea h member fun tion in turn following the de.nition of Poly. We have made it a lass and also indi ated what should be private and publi .

nition. .

delete[℄ oeff. Abhiram Ranade. void read(). publi : Poly(). i++) in >> oeff[i℄. } We next onsider the read fun tion. void Poly::read(){ out << "Give the degree of the polynomial: ". In this ase. Do not distribute 266 lass Poly{ private: int degree. float value(float x). Hen e the delete[℄ statement must be put in. 2011. If we do not rede. }. delete[℄ oeff. oeff points to some heap memory. This fun tion is the same as before ex ept for the line before a quiring new memory into oeff. // *** Added *** out << "Give oeffi ients from low to high: ". } Next we dis uss the assignment operator. Let us ensure that it is indeed orre t to add this line. Poly operator*(Poly onst & b). It sets oeff to NULL. in >> degree. float * oeff. that heap memory annot be pointed to by any other pointer. But sin e our program is obeying the distin t pointer rule. This is needed to adhere to the distin t pointer rule. Poly(Poly onst & p). // opy onstru tor Poly& operator=(Poly onst & rhs){ ~Poly(). i<=degree. (ii) oeff is not NULL. There are two ases: (i) oeff equals NULL: in this ase it turns out that delete[℄ does nothing! So there is no problem. Hen e before overwriting oeff we must return ba k the memory it points to. oeff = new float[degree+1℄. We have put in a default onstru tor. Poly::Poly(){ oeff = NULL. for(int i=0.

we would get the following behaviour when we make an assignment su h as b=a. b. oeff. oeff = a.degree = a.: b.ne this operator.degree. The .

sin e we are putting the value of a. then it is the last opy to some heap variable. they both . oeff is not NULL. So to prevent this we must exe ute delete[℄ b. oeff = a. oeff.rst line. oeff into b. oeff. oeff = a. oeff. However. b. oeff would likely violate both the last pointer rule as well as the distin t pointer rule! We know that if b.. before b.

oeff point to that new opy. oeff = new float[degree+1℄. for(int i=0. i. a=a. and hen e violate the distin t pointer rule! To prevent that.e. Do not distribute point to the same heap variable. for(int i=0. delete[℄ oeff. and make b. i<degree+1. if so. It is a tually a simpler version of the assignment operator.? This should also work. we simply make a opy of the on erned heap region. The simplest way to expli itly he k if the the left hand side and the right hand side of the assignment are the same. oeff[i℄. This is expressed in the ode below. degree = rhs. oeff[i℄. 267 Abhiram Ranade. we do nothing. // make opy to obey distin t-pointer rule out << "Exe uted assignment. return *this. Poly& Poly::operator=(Poly onst & rhs){ if(this == &rhs) return *this. i++) oeff[i℄ = p.\n". Hen e there is no need to invoke delete[℄ on it. } Next we dis uss the opy onstru tor. Finally.degree. Poly::Poly(Poly onst & p){ degree = p. i++) oeff[i℄ = rhs.degree. i<degree+1. } // opy onstru tor The . 2011. // to obey last pointer rule oeff = new float[degree+1℄. there is a small twist. What if someone writes a self assignment. The important dieren e is that the Poly variable being reated will not have its oeff member pointing to anything.

nal manner in whi h the oeff member of any stru ture an hange is when the stru ture is destroyed. say be ause ontrol is leaving the blo k in whi h a was de. Suppose a stru ture a is getting destroyed.

So we must return that memory ba k to the heap. and by the distin t pointer rule. oeff an potentially be pointing to a heap variable. it will be the last pointer to that variable.ned. Then a. This is expressed in the destru tor fun tion de.

Poly::~Poly(){ delete[℄ oeff. } Note that the destru tor is not to be alled expli itly in the program.ned below. The ompiler will automati ally all the destru tors on all variables de.

The remaining two member fun tions. value and operator*. will not need to hange.ned in a blo k when ontrol leaves a blo k. .

1 Remarks What did we a omplish with the new de. Abhiram Ranade. 2011. Do not distribute 268 16.4.

the new de. the main program with whi h we began the hapter an indeed be written. More generally.nition of Poly? First of all.

nition an be given to users. you an write something like Poly *ptr = new Poly. The users an reate poly obje ts using the given onstru tors. get them returned from fun tions. The users will not need to worry about allo ating memory or returning it { that will happen behind the s enes. and learly this will ause the memory issued the . perform operations on them. who an use it without worrying that there will be either memory leaks or dangling pointers. pass them to fun tions. ptr = new Poly. Clearly. One thing that is not allowed is reating the Poly obje ts themselves on the heap.

operator+. then everything will work beautifully. 2. whi h is what we wanted at the beginning of the hapter. The point however is that you an use the Poly type without having to know about the heap.5 Exer ises 1. De. operator-. operator<< and operator>>. if you use Poly in any of the ways data types have been used till the previous hapter.e. i. You will utilize memory eÆ iently. Write the other fun tions needed for representing polynomials.rst time to leak away. without using the operator new at all. 16.

then in the simplest de. T (x) are polynomials. Suppose S (x).ne the modulo operator % for polynomials.

nition. One way around this is to de. the remainder S (x) mod T (x) is that polynomial R(x) of degree smaller than T (x) su h that S (x) = T (x)Q(x) + R(x) where Q(x) is some polynomial. So it is important to make sure that there are no round-o errors as would happen if you divide. The main motivation for writing the modulo operator is to use it for GCD omputation later.

ne the remainder S (x) mod T (x) to be any kR(x) where k is any number. where R(x) is as de.

For simpli ity ignore this drawba k. In this assignment you are to write a lass using whi h you an represent and manipulate sets of non-negative integers. Of ourse this has the drawba k that the oeÆ ients will keep getting larger.ned above. you should now be able to ompute a remainder polynomial without division. 3. Hen e there will be no round o either. Spe i. Assuming that the oeÆ ients of the polynomials are integers to begin with.

( ) onstru t the interse tion of two sets. With your fun tions it should be possible to run the following main program. Use an array to store the elements in the set. . Do not store the same number twi e. (d) determine if a given integer is in a given set. ally. (b) onstru t the union of of two sets. (e) print a given set. you should have member fun tions whi h will (a) enable a set to be read from the keyboard.

set d = interset(a." << endl. )." << endl. b. else out << x << " is in one of the sets. int x.b).b. Do not distribute 269 main(){ Set a. in >> x. please ensure that you allo ate arrays of just the right size by . a. Abhiram Ranade. For the rest. set = unionset(a.b).read().d). The fun tion Set::read will be very similar/identi al to Poly::read. } if( both ) { out << x << " is in the interse tion ". 2011.print(). . } else if (none) out << x << " is in neither set. bool both = belongs(x. bool none = !belongs(x.read().

Eu lid's GCD algorithm works for .rst determining the size of the union/interse tion. 4.

it should move the polynomial ontained in sour e to dest. When invoked as sour e.move(dest).nding the GCD of polynomials as well. Consider the following new member fun tion for the lass Poly: void move(Poly &dest). using the iterative expression as well as the re ursive expression. and also set sour e to be unde. Write the ode for this. Will both versions ause the same number of heap memory allo ations? Whi h one will be better if any? 5.

6. is it ne essary to allo ate new memory? See if the Poly lass with the new move fun tion will improve the GCD programs onsidered earlier. You will have to de. this is meant to be an assignment in whi h the value is not opied but it moves. Templetize the g d fun tion so that it an work with ordinary numbers as well as polynomials. When the oeÆ ients are to be moved to dest. Implement this so that the last opy rule and the distin t opy rule are respe ted. Ee tively.ned.

Note that int is a onstru tor for the int type.ne a few more member fun tions as well as a onstru tor. i. int(1234) returns the integer 1234.e. .

Abhiram Ranade. Suppose you have a . 2011. Do not distribute 270 7.

. Write opy onstru tors et . you should allo ate a bigger array. If the array be omes full. the real array should be on the heap. so that the array will not have leaks et . Basi ally. Be sure to return the old unused portion ba k to the heap. pointed to by a member of your stru ture.le that ontains some unknown number of numbers. Develop an extensible array data type into whi h you an read in values. You want to read it into memory and print it out in the sorted order.

and the ..Chapter 17 Stru tural re ursion Consider the following mathemati al formulae: = and n X 1+ 3+ i2 = 4 5+ 1 2 2 2 3 2 7+ 4. 9 + . 2 n(n + 1)(2n + 1) 6 Both are orre t.

however. many programs are available for doing this. Where do we pla e the numerator and the denominator. and in this language. Our on ern in this hapter. and would like it if a program takes are of the rest! While this is somewhat tri ky. is not the validity or elegan e of these formulae. we would merely like to somehow state the formula whi h we want drawn. The program TEX has a language for spe ifying mathemati al formulae. how long do we make the lines denoting division? What if the denominator is itself a ompli ated expression as was the ase in the ontinued fra tion expansion for ? Ideally. Our on ern is mu h more mundane: how do we layout these formulae on paper. the most important amongst these is perhaps the TEX program developed by Donald Knuth. without worrying about any geometri al aspe ts.rst one is rather elegant. the two formulae above an be spe i.

ed as: i=1 \pi = \ fra {4}{1+\ fra {1^2} {3+\ fra {2^2} {5+\ fra {3^2} {7+\ fra {4^2} {9+\ddots}}}}} and \sum_{i=1}^ni^2=\fra {n(n+1)(2n+1)}{6} Given this textual des ription. While the spe i. TEX an generate layouts like the ones shown.

ation is somewhat rypti . you an probably see some orresponden e. You an 271 .

Or that nfra and n fra somehow denote fra tions. Do not distribute 1. 2. 2011. perhaps.1: Examples of output and input guess. x+1 x + +6 x+3 5 ((((x+1)/(x+3))+(x/5))+6) Figure 17. Even without pre isely understanding the language of TEX you an see that the spe i. a+b+ +d (((a+b)+ )+d) 4. Desired output Input required by our program a b+ (a/(b+ )) b (a+(b/ )) a+ 3. 272 Abhiram Ranade. that the symbol ^ is used by TEXto denote exponentiation.

ation does not ontain any geometri information. The spe i.

is the . using a ni e blend of s ien e and art. ation does not say. all this is determined by TEX. how long the lines in the dierent fra tions need to be drawn. Indeed. for example. How to layout mathemati al formulae.

Spe i. That. is to write a program that does what TEX does. is extremely ambitious! We will instead onsider a very tiny version of the formula layout problem. of ourse. 17. This will turn out to be a rather interesting appli ation of stru tural re ursion. We will then go on to another important.rst problem we will see in this hapter. but more lassi al appli ation: using trees to maintain an ordered set in memory.1 Layout of mathemati al formulae Our goal in some sense.

summations using the P symbol and so on. written in a language like the TEX language. Of ourse. ally. The . As you will dis over in the Exer ises. implementing more omplex operations su h as other operators. Our program must take any su h formula. and produ e a layout for it. all this will still be far from what TEX a omplishes. we will only onsider formulae in whi h only the 2 arithmeti operators + and / are used. is not mu h more diÆ ult. This layout must then be shown on our graphi s anvas. on e you master sum and division.

rst question. One possibility is to just use the TEX language. sin e that is well known. 1 . of ourse. we use a slight variation on the C++ style. Furthermore. even for the purpose of laying out mathemati al formulae. So to keep matters simple. Another possibility is to spe ify the formula in the style used in C++ to spe ify mathemati al formulae. but turns out it will make it slightly harder to write our program. This will work. it is very sophisti ated. is how should we spe ify the input to the program. However that seems too elaborate. after all we only have 2 operators. For example. it adjusts sizes of the text. as you will see later. whi h our program will not. 1 TEX is a omplete do ument pro essor.

but pla e the operands to the + operator as well as the / operator in parentheses. In the exer ises we will explore the issues in allowing less verbose input. be ause the rule says that the operands to every operator must be inside parentheses. So as a simple example. 2011. then the horizontal bar of the fra tion should align with the horizontal line in the + symbol. As you an see.1 gives some more examples. The divisor and the dividend must be entered with respe t to the horizontal bar. Figure 17. our program must write the summands respe tively to the left and right of the + symbol. when laying out division. if a summand is a fra tion. whereas in C++ you ould write a+b. Whereas. to spe ify this to our program you would have to write (a+b). we want the dividend to be above a horizontal bar. Do not distribute Spe ify the formula in the style used in C++. Output requirement: Here is how the output is to be generated. the input required by our program is somewhat verbose as ompared to what is required to spe ify the formula in C++. Also. whi h in turn is required to be above the divisor. 273 Abhiram Ranade. If a summand is a simple number or an identi. When laying out sums.

In general a mathemati al formula is built up by taking smaller mathemati al formulae.1 Stru ture of mathemati al formulae A fundamental observation is that a mathemati al formula has re ursive stru ture. The simplest.er. then it must align with the + symbol as in normal typing.1. Input format: 17. and onne ting them with operators. or more generally C++ style identi. or primitive mathemati al formulae are plain numbers or letters.

the formula b a is built up by taking the two formulae a and b + . using the addition operator.ers. The formula a is a primitive formula. and ombining them using the division operator. As an example. These onstitute the base ases for the re ursion. The re ursive stru ture be omes more obvious if we . while the formula b + is in turn built up by onne ting together the primitive formulae b.

sort of like the exe ution tree of Figure 10. nodes that are not leaves) are asso iated with an operator.e. A subtree. represents a subformula used to build up the original formula. in Figure 17.2 Representing mathemati al formulae in a program Figure 17.2(a). Internal nodes (i.e. nodes that have no hildren orrespond to primitive formulae.rst draw the formula as a rooted tree. Leaf nodes. Similarly. i. we should . suggests that to represent a formula.1. in Figure 17. + +18 +36 65 17. whereas the node labelled / on the right and the nodes below it together orrespond to the subformula x .2.e.xthe node labelled / on the left side and the nodes below it orrespond to the subformula x .2(b). Figure 17. any node and all the nodes below it.2 shows two formulae drawn as rooted trees. For example. the subtree in luding and beneath the node labelled + orresponds to the subformula b + .4. i.

e. or if the node is asso iated with a primitive formula. and if so whi h one. whether the node is asso iated with an operator. and then we should be done! It seems natural to use a stru ture to represent tree nodes. The natural way to represent onne tions between the nodes is to use pointers.g. and if so whi h one. So we de.rst represent the nodes of the tree. The stru ture should ontain the information asso iated with a node. and then represent the onne tions between the nodes.

.ne a stru ture Node as follows.

onsists of an identi. Do not distribute + / + / + + + 6 / a c b x 1 x 3 x 5 (a) (b) Figure 17. har op. i. }. +1 +3 5 // we give member fun tions later This stru ture an be used to express primitive as well as non primitive formulae. Node* rhs. 274 Abhiram Ranade. 2011.e.2: (a) Tree for b a (b) Tree for xx + x + 6 + stru t Node{ string value. Node* lhs. If a formula is primitive.

we will store that symbol or number in the member value as a hara ter string. In this ase. op = op1. rhs = rhs1. and we store pointers to the roots of the subformulae in the members lhs. rhs = NULL. Node* rhs1){ value = "".er or a number.rhs. op = 'P'. we store the operator in the op member. // onvention: 'P' in op denotes primitive formula. lhs = NULL. lhs = lhs1. } Node::Node( har op1. } // re ursive onstru tor Here is the . the formula must be a binary omposition of two smaller formulae. Node* lhs1. Node::Node(string v){ // primitive onstru tor value = v. It is useful to have onstru tors for both ways of onstru ting formulae. Otherwise.

+ Node aexp("a").rst way we an onstru t the representation for the formula b a in our program. .

275 Abhiram Ranade. exp(" "). new Node("a"). There is a dieren e between the two onstru tions. An important point to note here is that the operator new when used on a onstru tor all returns a pointer to the onstru ted obje t. Thus f2 will also be a root of the tree for the formula b a . &bplus ). new Node('+'. new Node(" ")) ). Or alternatively we an also onstru t a representation more dire tly: + Node f2('/'. short form for: Node bplus = Node('+'. &bexp). &aexp. &aexp. &bexp). Thus f1 will be the root of the tree for the formula b a . and an thus be said to represent the formula. f1('/'. 2011. In the . Do not distribute Node Node Node // Node bexp("b"). whi h is exa tly what we want as an argument to our re ursive onstru tor. however. Thus we an say that f1 represents the formula. &aexp. bplus ('+'. new Node("b").

rst onstru tion. all memory for the formula omes from the urrent a tivation frame. Read the formula from the input in the format spe i. the memory for f2 omes from the urrent a tivation frame. On e we have a representation for formulae. our task splits into two parts: 1. In the se ond onstru tion. all memory ex ept for the node f2 omes from the heap.

It is natural to de. Generate the layout for the onstru ted representation. 2.1 and build a representation for it using the Node lass.ed in Se tion 17.

ne member fun tions on Node whi h will generate the layout.1.3 Reading in a formula We now show how to read in the formula and build a representation. We onsider these steps in turn. It is easiest to write our ode as a onstru tor. For simpli ity. + 17. we will make two assumptions: (a) Ea h number or identi.

To read a hara ter from a stream infile. In the exer ises you are asked to write ode whi h allows longer primitive formulae and also spa es.get() whi h returns the next hara ter as an integer value. If the very . we an use the operation infile.er is exa tly one hara ter long. The idea is to read the input hara ter by hara ter. (b) there are no spa es inside the formula.

even though the formulae themeselves an be very ompli ated.rst hara ter read is a number or a letter. After that we re urse again! So our ode to read in a formulae is extremely simple. To read in (a). (b) an operator. . then we know that the user is supplying us a non-primitive formula. In that ase we know that we must next see in su ession (a) a formula. then we have indeed read a primitive formula and we an stop. and ( ) another formula. If what is read is the hara ter '('. and it had better be an operator. we merely re urse! Next we read a single hara ter.

Now we an write a part of the main program. >= 'a' && <= 'z' || >= 'A' && <= 'Z'){ lhs=rhs=NULL. // re ursively get the lhs formula infile. With this we have learly de. y)". y will be given by the user. The values x. whi h is the root of the tree representing the formula that is to be drawn. It is natural that the formula is presented to us as a node f. } } else if( == '('){ // does it start a nonprimitive formula? lhs = node Exp(infile). if( >= '0' && <= '9' || // Che k if it is a primitive formula. 2011. Do not distribute 276 Node(istream &infile){ har =infile. the formula will be read from the keyboard. 17.4 Drawing the formula on the anvas The input to the drawing step is a formula. As to where to draw it. } else out << "Error in input. and an indi ation of where it is to be drawn on the anvas.1.\n". value = .e.get() != ')') out << "No mat hing parenthesis. // re ursively get the rhs formula if(infile. Abhiram Ranade.get(). int main(){ Node f( in). just as we reated f2 earlier. presumably the user will tell us something like \Draw the formula below and to the right of the given point (x. You may type in something like (a/(b+ )) and it will reate f. rhs = node Exp(infile). op='A'.\n".get(op). i. } This will all our latest onstru tor with the parameter infile being in.

ned the spe i.

y. y0). Pro eeding in this spirit. ation of the problem: what we are given and what need to do. We are given a formula whose root node is f. y) on the s reen. Presumably our drawing ode will also be re ursive. we might say that the task of drawing the formula f at a position (x. and numbers x. How do we perform our task? By now you are perhaps wondering if everything with respe t to trees an be done by re ursion.rhs at a suitable position . We must draw f so that it lies just below and just to the right of point (x. y) an be a omplished if we know how to draw the left hand side formula f.lhs at a suitable position (x0 . and the right hand side formula f.

We are given f and so we know f. and then draw the operator or a bar between the two. Do not distribute 277 (x00 .rhs and the operator. But we do not know any of the positions. 2011. How do we . f. y00).lhs. Abhiram Ranade.

Where exa tly the symbol is to be pla ed depends upon the width required for f. Then how do we pro eed? Clearly. So it would seem that we should .rhs. then the symbol +.lhs to the left.gure them out? Suppose we try out some spe ial ases. we will need to draw f.lhs. and then f. Say f.op is '+'.

3(b) for the ase in whi h f. 1 2 1 and 1 2 1 all have essentially the same width and + + + a b a b a b height. the operator level of the summands must be aligned. However.3(a) for the ase in whi h f. Ea h of our summands is a fra tion.op is +. f. and has a horizontal bar whose position seems to determine how the summands align. and the + onne ting the summands must also be drawn aligned with the operator level. 1 1 2 + a+ b 2 + 2 1+ 1 2 1+ 1 1+ 1 a b a b a b 1+ 1 2 The summands 1 1. In these . and in Figure 17. As was noted in the des ription of how the output is to be produ ed (\Output requirement" from Page 273). Consider the following examples.rst determine the width required. Continuing to try out more examples.rhs as well. a 2 b. The general situation is onsidered in Figure 17. But their alignment in the two formulae is quite dierent! Clearly. we need to onsider something more than just the width and the height of a subformula. This position we will all the operator level. you will perhaps realize that it is ne essary but by no means suÆ ient to know just the width and the height of the subformulae.lhs. knowing the width is not enough { at what verti al position do we draw the + symbol? Perhaps we need to know the height of f. Clearly.op is /. the (verti al) position of the horizontal bar is very important.

In these .gures we have shown f.rhs by their bounding boxes. A bounding box is simply the smallest re tangle that overs the formula.f.lhs.

f. hl .lhs. Further de. wr and h. wl. hr to respe tively denote the width and heights of f.rhs respe tively.gures we have used w. f.

rhs will likewise also be known if we knew the widths. y are the oordinates of the top left orner of f. + in this ase. y + hl dl ) from Figure 17.lhs and f. then we an determine the mutual alignment. and des ents of f. we must .3(a). f. dl.lhs. then then oordinates for the enter of the operator + an be seen to be (x + wl + wo=2. f. However. Here wo is used to denote the width of the operator symbol. if we did know the values. heights or des ents of any of the formulae. if x.lhs.rhs. f. dr .rhs are respe tively denoted by d. As of yet we do not know the values of the widths.ne the des ent of a formula to be the distan e between the operator level and the bottom of the bounding box. whi h we an determine using the fun tion textWidth(f. The oordinates of the top left orners of f.op). So before we an think of drawing. For example. heights. The des ents of f.

height and des ent for ea h subformula in our formula. Turns out this an be done quite easily! For the ase when op is +. Figure 17.3(a) shows the relationships between the widths .gure out the width.

Do not distribute w_l w_o w_r max(h_l−d_l. 2011.3: Aligning layouts of lhs and rhs h . h_r−d_r) h h_l Operator level d_l h_r d_r w max(d_l. d_r) = d (a) w w_l h_l d_l h_/ d h_r d_r w_r (b) Figure 17. 278 Abhiram Ranade.

an be omputed using the fun tions textWidth and textHeight. . des ent. 2011. So our stru ture be omes: stru t Node{ Node *lhs.3. double width. wr ) h = wl + ho + wr (17. Node* rhs1). height and des ent. wh heights h. des ent in ea h Node stru ture. height. height. we an get the relationships when f.op is /: w = max(wl . height = textHeight(). Node(string v). ase '+': lhs->setSize(). height. void draw(float lx. Node( har op1. break.2) d = wr + ho =2 Here we have used ho to denote the height needed to pla e the horizontal bar to show the division. dr ) From Figure 17. hr and des ents d.e. it is most onvenient to have data members width. // to a tually draw } We have already given the implementations for the onstru tors. we an ompute the width. Sin e ea h formula has width. Further we will have a member fun tion setSize whi h will al ulate these numbers. i. Abhiram Ranade. *rhs. void setSize(). void Node::setSize(){ swit h (op){ ase 'P': width = textWidth(value). hl . har op. des ent = height/2. So learly. rhs->setSize().1) d = max(dl . Node* lhs1. The des ent for primitive formulae we will take as half the height. The width and height of primitive formula. string value. Do not distribute 279 w.3(b). using Equations 17. h = max(dl . dr : Clearly we have w = w l + wo + wr . text. dh ) + max(hl dl . wl . dl. Node(istream& infile). The implementation for setSize follows the ideas des ribed above. and des ent re ursively.2 and 17. hr dr ) (17. float ly).

ase '/': lhs->setSize(). break. Abhiram Ranade. width = max(lhs->width. height = des ent + max(lhs->height . The . break.lhs->des ent. height = lhs->height + Bheight + rhs->height.rhs->des ent). width = lhs->width + textWidth(op) + rhs->width. des ent = rhs->height + Bheight/2. } Clearly. rhs->width). rhs->des ent). we have 3 ases. default: out << "Invalid input. 2011. rhs->height . Do not distribute } 280 des ent = max(lhs->des ent. rhs->setSize().\n".

in whi h ase the width.rst is when the expression is a primitive expression. The des ent we have arbitrarily determined to be half the height.height are merely the width and height of the value text string. This should be .

op is + for whi h the operands must be drawn on either side.ne tuned by looking at the pi ture produ ed by the program. In this ase we . In the next ase.

height. and determine the parameters as per Equations 17. In the last ase. 17. we will hange our spe i.5 Drawing the pi ture For simpli ity. We then determine width.rst all setSize for the rhs and lhs operands.3. op equals / for whi h the operands must be drawn one above the other.1. and as ent as per Equations 17. Again we all setSize on the operands.2.

and the operator line is at a distan e ly from the top. We will de. y) of the top left orner of the pi ture as an input. In the Exer ises you are asked to modify our ode that the formula is drawn so that its top left orner of the pi ture is at the given position. Instead of giving the oordinates (x. ation a bit. say we are required to draw our pi ture su h that the left edge of the pi ture is at a distan e lx from the left edge of the window. This would be the natural request if we are pla ing our drawing inline with the text that is being written.

This is given in the ode below. we an re ursively de ide where ea h subexpression must be drawn. float ly){ swit h(op){ ase 'P': drawText(Position( lx+width/2. . break. void Node::draw(float lx. ly).value). ly). The implementation will of ourse be re ursive. Sin e we know all sizes. ase '+': lhs->draw( lx.ne a draw member fun tion taking these two numbers lx. ly as arguments.

ly-Bheight/2-lhs->des ent). drawText(Position( lx+lhs->width+textWidth(op)/2. ly)). lhs->draw( lx+width/2-lhs->width/2.\n". ly). ly+Bheight/2+rhs->height-rhs->des ent).imprint(). } The simplest ase is of ourse the base ase. we simply write the orresponding text. 2011. when the expression is primitive. ase '/': Line(Position( lx. Remember that the fun tion drawtext requires the enter of the text to be spe i. default: out << "Invalid input. rhs->draw( lx+width/2-rhs->width/2.op)). Do not distribute } 281 rhs->draw( lx+lhs->width+textWidth(op). break. ly). break. Abhiram Ranade. ly). Position( lx+width. In this ase. string(1.

f. lhs must also be drawn with arguments lx. the lhs must be aligned with the left boundary of the given expression. the operator line level.7 Remarks Re ursive stru tures appear in many real life situations. The ode for the re ursive ase when the operator is / is similar. the administrative heirar hy of an organization is re ursive. dire tly gives the y oordinate of the enter. Finally we must draw op at its pla e. For the operator +. the operator line of the given expression is identi al to the operator line of the operands. Node f( in). Note that ly. to whom report further deputies. int main(){ initCanvas("Formula drawing"). there is a dire tor/president/prime ministers.200). For example.1.ed. This is what the above ode does. Further. Note that the expression string(1. The rhs has to be oset by an amount equal to the width of lhs.draw(200. } 17. to whom report deputies. e.1.op) is merely a all to a string onstru tor. whi h returns a string ontaining 1 repetition of op.setSize().g. . ly. 17. Hen e. The ode for re ursive expressions is fairly natural. // oordinates pi ked arbitrarily wait(5). and also the width needed to draw the operator op.6 The omplete main program Now we an easilty omplete the main program. whi h we al ulated earlier. hen e the above ode al ulates the x oordinate of the enter by adding half the width. f.

2011. and the element joining the subtrees. the dire tor will orrespond to the root. In the ase of mathemati al expressions. Do not distribute 282 It is natural to asso iate a tree with a re ursive stru ture. Abhiram Ranade.g. e. The substru tures are denoted as subtrees. the operator orresponds to the root. and the sub expressions orrespond to the subtrees. You may be wondering why we require that the formulae to be layed out be spe i.

But you an see that other operations might also be useful. or automata theory. However. As the program exe utes. in the exer ises you are en ouraged to think about it. In addition. insertion.g.e. If you pursue further edu ation in Computer S ien e.2 Maintaining an ordered set We onsider the following abstra t problem: how to maintain a set whose elements an be integers. removing an element from a set. why not just spe ify them as they might be in C++? It turns out that getting a program to read formulae in C++ like languages is a lassi al omputer s ien e problem.ed in our verbose format. i. For now suÆ e it to say that reading C++ style expressions is a diÆ ult problem. e. integers an get added into the set. 17. the program must determine if x is present in the set. or . in its most general setting. given some integer x. the program must respond to membership queries. and membership. we only onsider these two operations. you will perhaps study it in a ourse on ompiler onstru tion. For simpli ity.

The simplest way to store a set is to use an array.g. The ideas we dis uss for our simple problem will be of use in these more ompli ated situations as well.nding the number of elements smaller than a given number z. To determine if an element is present. when a new element is to be inserted. a stru ture ontaining the roll number and marks of a student. Even more generally. A slight improvement is to keep the elements sorted in the ve tor. Then we will be able to perform membership queries using binary sear h. we an s an through the ve tor. The s anning operation. we will need to . whi h would go very fast. however. Then you might merely want to know if a student belongs to a lass (membership). we simply use the push ba k fun tion. you ould let the elements of the set be omplex obje ts. e. is rather time onsuming: we need to examine every element stored in the ve tor. as you will dis over in the exer ises. However. or you might want to know the number of students who got fewer marks than some number z. To add an element. or a ve tor (Chapter 18).

and shift down the elements larger than it. Then we dis uss how the tree an be represented on a omputer. First we dis uss the orresponden e between a set and a sear h tree onsidered abstra tly. The left bran h (if any) onne ts the root to the left subtree. .2.nd its position. and the right bran h (if any) to the right subtree. So again this is unsatisfa tory. This operation will on the average require us to shift half the elements. and thus is quite time onsuming. Ea h node has upto two outgoing bran hes.1 A sear h tree There is a way to organize the elements of the set so that insertions as well as membership queries an be done very fast: we store them in a so alled sear h tree. A sear h tree is a rooted tree in whi h elements of the set are asso iated with ea h tree node. 17. denoted left. and right.

ex ept that we do not have the member op. 70g. 35. 78. 56. We do have a member value whi h will hold the set element . stru t Node{ Node *lhs. In ea h ase. So the tree in ( ) will not represent any set.2. Do not distribute 34 56 50 18 40 77 30 70 (a) 35 12 86 60 34 10 18 30 36 51 65 78 93 56 (b) 18 30 70 (c) Figure 17. The stru ture needed is almost the same as what we had for storing mathemati al expressions. 50. 77. 40. A subtree with no bran hes is alled a leaf. 18. *rhs. we have shown the value of the element stored at ea h node. whi h is not needed here. 34. 60. 30. 12. while the one in (b) would represent f10. In ( ).4 shows example of a sear h tree (part (a). 93g. 51.(b) and non-example ( ) of sear h trees A subtree is likewise a root with upto two bran hes.4: Examples (a). 86. 283 Abhiram Ranade. int value. } This is identi al to what we had in Se tion 17. as per our s heme. 65. It should be lear how to represent sear h trees.(b)) and a non-sear h tree (part ( )). Here is the key property that we require for a tree storing elements to be a sear h tree: Values of elements in the Value of element Values of elements in the right subtree of node v at node v left subtree of node v Figure 17. 30.1. 2011. Thus the tree in (a) would represent the set f18. the subtrees beneath the node with element 34 do not satisfy the sear h tree property: the right subtree is required to ontain elements larger than 34 but it a tually ontains the element 30. 36.

we will assume that somehow the trees that we en ounter will be balan ed. So we get to the node ontaining the number 65. we would de ide that we only need to sear h the right subtree. If the number happens to be x. 2011. both subtrees under ea h node had exa tly the same number of nodes. Sin e we only know the root of the tree. then we re urse on the right subtree. Finding that x is bigger. As before the members lhs and rhs will pointers to the root nodes of the left and right subtrees. if x is larger than the number at the root. Then we would ompare x to the number at the root. so we use that to get to root of the right subtree. you would be right.e. we know we must go to the left subtree. then we know that it an only be in the left subtree. Sin e x is smaller than 65. If the number at the root is not x. 17. For now. 77.4(b). This time we realize that x whi h we are looking for is smaller. So we follow the left pointer this time and get to the node ontaining the key 60.4(b was balan ed. The re ursion stops if we are for ed to sear h an empty subtree { if that happens we know that the number is not present and we return false. If at this point you feel that our argument is too sli k. we need to follow the left or right pointers. How do we do this? Remember that when we build the tree. We did not examine the other nodes.e. But there is no left subtree for the node ontaining 65! So in this ase we have determined that our number x is not present in the set. say determine whether some number x is present in the tree. then we an immediately respond with a true response. Thus now we an re urse on the left subtree! Similarly. So our problem is: we know the root of the tree that ontains the elements. 60.5. This time we he k and realize that x is in fa t larger. The tree of Figure 17. So this is how we an give a fast response. and 65. This is be ause of the sear h tree property: the numbers in the right subtree an only be larger than the number at the root.2. Suppose now the user presents us a membership query.2 The general idea We explain with an example why sear h trees are useful for storing sets. we will only be able to refer to the root dire tly. Abhiram Ranade. we an only ompare x with the number stored at the root. If the tree is unbalan ed. yet we dedu ed that the number x = 63 ould not have been present in the other nodes: be ause we know that the tree obeys the sear h tree property. We take up this aspe t in Se tion 17. whi h is 77. To get to the other nodes. i. Do not distribute 284 stored at the node. So we return false as the answer. So next we ompare x with the number stored there. If x is smaller. The root node ontains a pointer to the root of the right subtree. So we know we must sear h the left subtree beneath 77. i. Noti e that we have been able to get to an answer by examining a very few nodes: those nodes ontaining 50. So we ask whether x is smaller or larger than the number at the root. then we need to do more work. try to determine if x is present in the right subtree. Suppose we have somehow onstru ted the sear h tree in memory.2. and we wish to determine if x is present at any node of the tree. then the eÆ ien y an be ome mu h worse. suppose we have in memory the tree in Figure 17. or nearly balan ed. As an example. so there is no need for us to ompare x to them. The argument given above depends very mu h upon the shape of the tree in whi h the set was stored. and we are given x. So we follow the right bran h out of the node ontaining number 60. This assumption an be justi. Suppose we want to know if x = 63 is in the tree. 50.

ed. as you .

Then we .2. For this. Do not distribute 285 will see in Se tion 17. Next we onsider the operation of inserting elements into the set. we do something similar to he king if a number is present.5. Suppose we wish to insert the number x. 2011. Abhiram Ranade.

This does not quite work in the present ase. For onvenien e. whi h will ontain a data member we will all root. Set(){proot = NULL. we re ursively try to insert in the right subtree.2. or else the sear h tree property will be violated. but we have put in a onstru tor whi h sets the member proot to NULL. then we know that it must be inserted in the left subtree. // pointer to tree root. 17. then that obje t will store a value. we represent a set by a pointer to the node denoting the root. How do we represent an empty set? If the representation ontains any Node obje t whatsoever. If x is smaller. So we re ursively try to insert in the left subtree. Similarly if x is larger than the number at the root. Now if we want to represent the empty set. There is a slight te hni ality that we need to onsider.rst he k the number at the root.e. and hen e will not represent an empty set. whi h will point to the root node of the tree. In the last se tion.} // more to ome. Instead. stru t Set{ Node* proot. The pre ise details will be ome lear when we give the ode. i. Given this de. we used the root node of the tree as the representative of the tree. we will put the pointer to the root inside a lass Set.3 The implementation We will indeed represent a set as a tree. indi ating that the set is empty. } The lass will have more member fun tions. we merely set this pointer to NULL. the point from whi h we an get a ess to the rest of the tree. So learly we annot represent a set by the node denoting the root of the tree.

Instead of using it as given earlier. We will also hange the Node stru t slightly. and we will have de lared a set in our program. we will de. This is ni er than saying Node* mySet.. // automati ally initialized to NULL. we may write Set mySet.nition. by the onstru tor.

}. rhs. int value. Noti e that this de. stru t Node{ Set lhs.ne it as follows.

nition is really the same as the old. Many programmers might sti k with the old de. after all Set ontains no other data members ex ept proot of type Node*. But making the members lhs. rhs of type Set will make the ode easier to read.

so the Exer ises ask you to do that also.nition. .

The ode for the fun tion follows dire tly from what we dis ussed earlier. the element is not present. else{ if(elt == proot->value) return true. Do not distribute 286 We will implement the membership query as a bool fun tion find taking as argument the element to look for. } } As we said. Abhiram Ranade. else return proot->right. else if(elt < proot->value) return proot->left.find(elt). 2011.find(elt). hen e the . bool Set::find(int elt){ if(proot == NULL) return false. if we rea h an empty tree.

Else if elt is smaller than proot->value. elt. Before we dis uss insertion. If elt is equal to proot->value. we must sear h the left subtree. but does nothing to the other members Is this OK? If nothing is spe i. Similarly the right. hen e the value stored at the root is proot->value. } This sets the value member to the given value. we have dis overed that elt is indeed in the set. it is useful to see a onstru tor for Node. with the value at the root of the set. Else we ompare the element being sear hed. Node::Node(int v){ value = v.rst statement returns false. and so we return true. Note however that Set merely ontains a pointer proot to the root. proot->left.

ed. then these members will be initialized by their default onstru tors. The ode is re ursive and follows our dis ussion. rhs would indeed get initialized orre tly. So in this ase. if(elt < proot->value) proot->left. } } If our set is empty. then proot will be NULL.insert(elt). void Set::insert(int elt){ if(proot == NULL){proot = new node(elt).} else{ if(elt == proot->value) return. // no need to insert again. We will implement insertion by a fun tion insert taking the element to be inserted as the argument.insert(elt). But the default onstru tor for Set auses the member proot to be set to NULL. Now we ome to insertion. This is what the . else proot->right. So the members lhs. rhs. lhs. we will insert a node ontaining the new element.

Similarly for the right. we do nothing. If the set is not empty. The exer ises ask you to de. there is no need to insert the same element again. But if the value being inserted is smaller.rst statement does. then we will insert into the left subtree. We will he k if the value at the root is equal to the element being inserted. and in this ase we will ome to the se ond line of the fun tion. if so. then proot must be non NULL.

e. . most operations on trees an be naturally ta kled using re ursion. As you might guess.ne other operations. printing the set.g.

5: Other trees representing the same set as Figure 17.2.4 A note about organizing the program Note that our de. 2011.4(a) 17. 287 Abhiram Ranade. Do not distribute 18 56 34 40 34 70 56 70 18 40 (a) (b) Figure 17.

nition of Node refers to the de.

nition of Set. Whi h one must pre ed the other? The de. and vi e versa.

nition of Set only refers to a pointer to Node. Hen e we an de.

ne that after putting a forward referen e to Node. The de.

Hen e it must ome after the de.nition of Node however mentions a member of type Set.

The implementation of the member fun tions in Set an ome any pla e following the de.nition of Set.

nition of Set.5 On the eÆ ien y of sear h trees We .2. 17.

There an be other trees also. Figure 17. the worst is the one in Figure 17. The third smallest is at its right hild.5(a). Clearly. the time required to answer membership queries will depend upon whi h of these 42 trees has arisen during the exe ution. if the set had been stored as Figure 17. The se ond smallest is at the right hild of the root. the smallest value is at the root.5 give two additional trees whi h ontain the same numbers as Figure 17. In this. and go rightward.rst observe that there an be many binary sear h trees that ontain a given set of numbers. and so on. then the we would .5(b). examining every node in the tree. Of these trees. Then the sear h would start at the root.4(a). Our program will build this \tree" if the numbers were inserted in as ending order. in fa t you should be able to prove that a set with 5 elements an be represented by 42 trees. In omparison. Suppose the user asked to sear h for 100.

then we would like all su h paths to be short.5(b) is essentially like sear hing in a sorted ve tor.rst ompare 100 to the value 56. and then to the value 70. So learly the tree of Figure 17. and on lude that 100 is not in the set. So perhaps we ould make a general observation: our find fun tion will examine the values stored in some path starting at the root and ending at the leaf. Indeed.5(b) is bad for the purpose of he king if 100 is in the set. So if we want the program to run fast. you will observe that sear hing in the tree of Figure 17. It is ustomary to de.

Thus our hope is that as the program exe utes. then the expe ted . Then if the order to insert is hosen at random. Theorem 5 Suppose numbers from a ertain set jS j are inserted into a sear h tree using our insert fun tion. the tree we get has small height.ne the height of a tree as the length of the longest root leaf path in a tree.

This is not entirely trivial: make sure your program works orre tly for input ((x+3)*(x-2)). 2 ln jS j. then we would get just one path of length 1000 { that would be the height. What if the numbers in the set got inserted in as ending order. So the height of this tree would be 9. Further.e. it should be possible to draw x uv . 17. Allow the impli it multipli ation operator. and say hanging the root. The other extreme is a tree in whi h we keep on inserting nodes as lose to the root as possible.Node("x"). then two nodes onne ted to ea h of these. Suppose we have a set with size 1000. Node("y")) whi h will print as xy . Or alternatively. till be inserted 1000 nodes. but might take very long if you are unlu ky. or some su h bad order? In that ase there are advan ed algorithms that try to balan e the tree as it gets built. 288 twi e the natural log of the number of elements The proof of the theorem is outside the s ope of this book. Let us try to understand what the theorem says using an example. Then on the average we expe t to see that the height will be at most 2 ln1000 14.6 Balan ing the sear h tree You might be bothered that the above program will work fast \on the average".2. Do not distribute height of the tree smaller than in the set. Clearly. 3. and so on. In other words.3 Exer ises 1. You will see that you may need to add parenthesization to the output. '+' and '-'. . For simpli ity. 2. on the average our find and insert fun tions will run fast.e. and the remaining 1000 256 128 1 = 489 nodes at level 9. if the numbers ame in in reasing order. With su h rebalan ing. But this is outside the s ope of this book. This is done by modifying an already built tree. it is indeed possible to ensure that the height of the tree remains small. Node('^'. 17. i. 4 nodes at distan e 2 and so on till 256 nodes at distan e 8. So we would start by inserting two nodes dire tly onne ted to the root. So we would have 1 node (the root itself) at distan e 0. but the exer ise asks you to validate it experimentally. Abhiram Ranade. So it is ni e to know that on the average we are likely to be mu h loser to the best height rather than the worst. rebalan ing algorithms have been developed that also run very fast. you ould parenthesize every expression when in doubt. Extend the formula drawing program so that it allows the operators '*'. 2011. Add an operator '^' to denote exponentiation in the formula drawing program. i. 2 nodes at distan e 1. whose elements are inserted in random order into our tree. Thus when we perform membership queries (or further insertions) we expe t to ompare the given number with the numbers in at most 15 nodes in the tree. You ould also ask what are the worst and best heights possible for 1000 nodes.

Do not distribute 4. 2011. Also if the user asks that the formula be entered at some given point. The asso iated . 5. and onstru ts an expression based on what it reads there. Show how you ould do this. Write a onstru tor fun tion whi h takes as input a single referen e argument. infile whi h is a referen e to an istream. Suppose the user gives the position of the top left orner of the bounding box of the formula. 289 Abhiram Ranade.

le should ontain valid expressions but written in a pre.

x form. Note that in the pre.

the operator omes .x form.

Thus your onstru tor will also be re ursive. For simpli ity assume that ea h primitive expression is a single hara ter. Observe that this way of writing expressions also has a re ursive stru ture. Thus b a will be written as (/ a (+ b ). and every operator is parenthesized. Further assume for simpli ity that there are no spa es in the input.rst. Thus the above expression would appear in the .

The expression infile. Note that get is a member fun tion on istreams that an be used to read single hara ters. Thus infile. 7.get() reads the next hara ter from infile and returns its value.peek(). Modify the ode above so that it is allowed to ontain spa es.le as (/a(+b )). 6. returns the next hara ter in the .

Assume that onse utive primitive expressions will be separated by a spa e. and the expression E to be integrated. You ould require this to be spe i. the upper limit U. Use this to modify the ode above so as to allow primitive expressions to be longer than a single hara ter. whi h takes as arguments 3 formulae: the lower limit L . How will you represent integration with lower and upper limits. 8. you should be able to draw formulae su h as + Z 1 0 x2 dx x2 + 1 Hint: The best way to do this is to use a ternary operator.le without a tually reading it. say denoted by the letter I. and the integrand? In other words.

9.ed as (L I U E). As we have de.

You ould think of bra kets being a unary operator. it be written as (F B). you ould ask that if a formula F is to be bra keted. Extend our program to allow this. Sin e it is our onvention to put the operator se ond. say B. our formulae annot in lude bra kets.ned. Make sure that you draw the bra kets of the right size. 10. You may want to think about how the program might hange ifb the formula to be layed out is spe i.

This is the ase if the subsequent operator. if any. but you are en ouraged to think about it. Note that your job is not only . has the same pre eden e as +. as in the present ase. So you need to look ahead a bit to de ide stru ture to onstru t. i.ed in the standard C++ style. The key problem as you might realize. is that after reading the initial part a+b of the input. you are not sure whether the operator + operates on a. then the result of the division must be added to a.b.e to draw a + the input is given as a+b/ rather than (a+(b/ )) as we have been requiring. if the subsequent operator has higher pre eden e. This is a somewhat hard problem. However.

Add a deriv member fun tion. You will noti e that the result returned by deriv often has sub-expressions that are produ ts in whi h one operand is 1 and sums in whi h one operand is 0. Do not distribute 290 to write the program. but also argue that it will orre tly deal with all valid expressions that might be given to it. Su h expressions an be simpli. Abhiram Ranade. 2011. 11. You should be able to draw the derivatives on the anvas. d(uv ) du dv = v +u dx dx dx This will of ourse be re ursive. of ourse. whi h should return the derivative of a formula with respe t to the variable x. i.e. Use the standard rules of dierentiation for this. 12.

13. Add a simplify member fun tion whi h does this.ed. This will also be re ursive. Suppose you want to represent sets using just the Node de.

2. whis is really of type Node*. that those were member fun tions for Set. Then to reate a set mySet whi h is initially empty. To implement membership and insertion queries.2. I would write: Node* mySet = NULL.1. int elt){ if(set == NULL){set = new node(elt.NULL.nition from Se tion17. else insert(set->right. Here is a suggested adaptation of insert: void insert(node* set. elt). so they annot be ome member fun tions for Node.3. Thus they must be ome ordinary fun tions. } } Do you think it is a faithful adaptation? Does it work? Hint: Be areful about whether you should use all by referen e or by value. Here is an adaptation of the .NULL). we ould merely adapt the fun tions insert and find of Se tion 17.} else{ if(elt < set->value) insert(set->left. elt). Note however.

nd method. elt). bool find(node* set. else if(elt < set->value) return find(set->left. else return find(set->right. } } . elt). else{ if(elt == set->value) return true. int elt){ if(set == NULL) return false.

Do not distribute 291 Again. Abhiram Ranade. Hint use re ursion: . is this a faithful adaptation and will it work? 14. Add a print member fun tion to Set. 2011.

.rst print the members in the left subtree. Repeat 100 times and take the average. 16. 15. Now use the ount value to respond to smaller. Experimentally verify Theorem 5. Measure the height of the resulting tree. then the value stored at the urrent node. You will need to update ount values suitably whenever you insert elements. Hint: Add a member ount to ea h node whi h will indi ate the number of nodes in the subtree below that node. Let n denote the number of elements in the set. and then the value in the right subtree. Assume without loss of generality that the elements in the set are integers 1. Suppose that you are to print a message \Empty set" in su h ases. : : : . n. 2. Add a member fun tion with signature int smaller(int elt) whi h returns the number of elements in the set smaller than elt. Note: Your answer to the previous problem will likely print absolutely nothing for an empty set. Repeat for dierent values of n and plot average tree height versus n. Run the insertion algorithm by generating numbers between 1 and n (without repla ement) in random order. Hint: Use one non-re ursive member fun tion whi h alls a re ursive one.

The library is fairly large. write it as a fun tion or a lass. do good memory management if needed. just as arrays an be. more powerful. In parti ular we will study the template lasses ve tor and map whi h are among the so alled ontainer lasses supported in the library. But of ourse. We have hinted in Se tion 17. They an be used to hold olle tions of obje ts. Indeed you may think of these lasses as more exible. But we an do even better: if some ideas are used outstandingly often. It is worth understanding the library. the fun tions and lasses in the library use the best algorithms.2 that arrays might not be the best way to store every olle tion. Also. be ause familiarity with it will obviate the need for a lot of ode whi h you might otherwise have written. Indeed the SL lasses su h as map employ ideas su h as balan ed trees for storing elements. and invoke the fun tion or instantiate a lass obje t instead of repeating the ode. as users you only need to know the spe i. and have been extensively tested. whi h you get as a part of any C++ distribution.Chapter 18 The standard template library An important prin iple in programming is to not repeat ode: if a single idea is used repeatedly. extensions of arrays. Thus it is strongly re ommended that you use the library whenever possible instead of developing the ode yourself. and so we will only take a small peek into it to get the avour. perhaps the language should give us the fun tions/ lasses already! This is the motivation behind the development of the standard library.

This lass is extremely onvenient. we will use the priority queue lass in Chapter 21. we program variations on the marks display program of Se tion 12. In addition to ve tor and map. and need not worry about how they are implemented.2. we will also study the string lass meant for storing hara ter data. At the end of the hapter we will give a qui k overview of the other lasses in the standard library. and you should use it by default instead of using hara ter arrays. ation of the lasses. Our . As running examples of the use of the standard library. Of these.2.

You know enough C++ to solve all 292 . The main interesting feature here is that the program is not given the number of marks before hand. and so will need a exible data stru ture in whi h to store the marks. and we are asked to print out the marks in in reasing order of the roll number or in non-in reasing order of the marks. the tea her enters marks along with the names of the students. Then the program must wait for students to enter their names. In the third variation. the tea her also enters the roll number of ea h student.rst variation is extremely simple: the tea her enters the marks and the program must print them out in the sorted order. In the se ond variation. the program must print out the marks re eived. and on re eiving the name of any student.

To use the template lass ve tor you need to in lude a header . you will be able to solve them with mu h less programming eort. more general variation of one dimensional arrays. you will see that using the Standard Library. Abhiram Ranade. and you have already solved some of them. 18. 2011.1 The template lass ve tor The template lass ve tor is meant to be a friendlier. However. Do not distribute 293 these variations.

For example. Thus v3. // ve tor of 5 elements. ve tor<float> v2.le: #in lude <ve tor> A ve tor an be reated by supplying a single template argument. ve tor< har> v4(5.e. But other onstru tors are available for reating ve tors with a given length. they ontain no elements. we may reate a ve tor of int and a ve tor of float by writing the following. i. assuming the de. the type of the elements.size() would evaluate to 10. ea h set to 'a'.'a'). // ve tor of 10 elements. to know the size you simply use the member fun tion size. For example. ea h of type short. ve tor<int> v1. These ve tors are empty as reated. A ve tor keeps tra k of its own size. // opy of v3. and in addition. ve tor<short> v5(v3). a given value. you might write: ve tor<short> v3(10).

nition earlier. v3. You an a ess the ith element of a ve tor using the subs ript notation as for arrays. unlike arrays. the index must be between 0 (in lusive) and the ve tor size (ex lusive). you an assign one ve tor to another. So if v. For example. The usual rules apply.push_ba k(22). and of v3 to 11. then we may write v = w. you ould write v3[6℄ = 34.push_ba k(37). v4[0℄ = v4[0℄ + 1.w are ve tors of the same type. The argument to the method push ba k would onstitute the last element. These statements would respe tively in rease the length of v1 to 1. A whole bun h of operations an be performed on ve tors. You an also extend the ve tor by writing: v1. For example. .

You might also wonder. spe ially if v was earlier mu h longer than w. Do not distribute 294 whi h would make v be a opy of the ve tor w. There is a very onvenient answer to this: Dont worry about it! The memory is managed . This happens even if v. all the elements are opied. You should realize that although the statement looks very small and simple. and hen e the time taken will be roughly proportional to the length of w. 2011. what happens to the memory in whi h the old ontents of v were. Abhiram Ranade.w had dierent lengths originally. The old values that were ontained in v are forgotten.

newValue). destru tors.4.4. w.ne. no dangling pointers. But you an also set the size arbitrarily by writing: v.pop ba k().resize(newSize. in the style dis ussed in Se tion 16. there will be no memory leaks.resize(newSize). assignment operators of the lass ve tor have already been written. These will get alled automati ally without you having to worry that they even exist! You treat a ve tor like an ordinary stru ture.1. in fa t you should not yourself use the operator new with ve tors. The onstru tors. You an shrink a ve tor by one element by writing v. The . opy onstru tors. In the terminology of Chapter 16. as we indi ated in Se tion 16.

1.4.1.2 18. This is dis ussed in Se tion 18.rst statement would merely hange the size. 18. and if the new size is greater.2 Index bounds he king Instead of using subs ripts [℄ to a ess elements. The se ond statement would hange the size. This will . then the new elements would be assigned the given value. you an use the member fun tion at.1 Inserting and deleting elements It is possible to insert and delete elements from a ve tor.

at(1). for(int i=0. This will ause the .at(0) = v. the program will halt with an error message. ve tor<int> v.push_ba k(i*10). If the index is outside the range. v.rst he k if the index is in the range 0 (in lusive) to array size (ex lusive). Note that the at fun tion an be used on the left as well as the right hand side of assignments. i<10. i++) v.

50. 10. i.e. 20. 70.3 Sorting a ve tor The standard template library ontains many useful fun tions whi h you an a ess by in luding another header . 80. 30. 40. 18.1. 60. 90.rst element to be opied to the zeroth. at the end v will ontain 10.

le. #in lude <algorithm> If you in lude this .

you simply write: . sorting a ve tor v is easy.le.

i. The expression v.end() is also an iterator. // read into the ve tor marks sort(marks. i<marks. 2011. v. 18. The expression v.e.4 Marks display variation 1 We merely read the marks into a ve tor. whi h we will dis uss in Se tion 18.4. // sort the ve tor for(int i=0. The program above will read in all the marks (assuming the marks .size().begin(). 295 Abhiram Ranade.end() indi ates that the portion to sort ends at the end of the ve tor.begin().end()). and v.begin() evaluates to an iterator.1. marks.push_ba k(nextVal). Note the use of // standard array syntax. By writing v. int main(){ ve tor<float> marks. while( in >> nextVal) marks. Do not distribute sort(v. The arguments to the sort fun tion indi ate what portion of the array to sort. is a generalization of pointers. In other words. An iterator.end()). the elements in v will be rearranged so that they appear in non-in reasing order. and then use the sort fun tion to sort. the entire array is to be sorted.begin() you have indi ated that the portion to sort starts at the beginning of v. } int nextVal. // output. That's it! This fun tion will sort the ve tor v in-pla e. i++) out << marks[i℄ << endl.

and then print out what it read.1. The sort fun tion is a tually more interesting. 18. then sort the ve tor. as we will see shortly.le is redire ted to the standard input).5 Marks display variation 2 Suppose now that our marks .

The natural way to write this program is to use a stru ture in whi h to read the roll number and marks. // ignore this member fun tion // for now . stru t student{ int rollno. followed by the marks.rollno. } }. bool operator<( onst student& rhs) onst{ return rollno < rhs. Again.le ontains lines of the form: roll number of the student earning the marks. float marks. we are not expli itly given the number of entries and the goal is to print out the list in a sorted order. We would then use a ve tor of stru tures.

we must somehow spe ify how to ompare stru tures. student s. and whi h should be onsidered smaller (and hen e must appear earlier in the result). } So all that remains is the ode to sort. 18. Abhiram Ranade. Do not distribute 296 int main(){ ve tor<student> sve .size(). Clearly.1.6 Customized sorting There are two ways of doing this. i<sve . 2011.push_ba k(s). it is not lear what it means to sort a ve tor of stru tures. while( in >> s.marks.rollno){ in >> s. Note that in general.marks << endl. } // put ode here to sort ****** for(int i=0.rollno << " " << sve [i℄. sve . i++) out << sve [i℄. The .

rst is to de.

ne the operator < for omparing stru ts. We have given a de.

Basi ally.nition of this in the ode above. the de.

their roll numbers will be ompared.rollno.nition says that when we write an expression lhsStudent < rhsStudent.rollno < rhsStudent. and lhsStudent will be onsidered smaller if lhsStudent. Given this de.

as dis ussed in Se tion 11. This will sort the array so that elements are arranged in non-de reasing order of rollno.4. However.nition. There is another. more general way to a hieve this same ee t: we somehow pass a fun tion to sort whi h sort an use to ompare the obje ts it is sorting. Perhaps the most natural way to pass a fun tion is to pass a pointer to it. in this ase a dierent me hanism is required: we must pass a so alled fun tion obje t. it suÆ es to repla e the line marked ****** in the ode with the statement: sort(marks.begin(). we an simply use the sort fun tion as before! In other words.7 Fun tion Obje ts The .1. as before. marks. whi h we dis uss next.end()). 18.

rst important point to note is that in C++. and f. a2 are the operators.a2 is simply evaluating an expression in whi h the operator is the fun tion all operator denoted as (). So we ome to the se ond point: we an de. a1. a fun tion all is also an operator evaluation! Calling a fun tion f with arguments a1. This way of viewing a fun tion all might appear strange. but there is a reason for it.

This in ludes the fun tion all operator () as well! Thus if we de.ne the behaviour of any operator for any lass.

ne operator() .

stru t D{ bool operator()( onst student &lhs. Note that we have de. and instan eOfC is a variable of lass C.rollno < rhs.rollno. Abhiram Ranade. } } instan eOfC. } } instan eOfD. stru t C{ bool operator()( onst student &lhs.marks. 2011. onst student &rhs){ return lhs. Do not distribute 297 for a lass C.marks < rhs. onst student &rhs){ return lhs. then we an all instan eOfC as a fun tion! Here is are two examples.

The fun tion all operators in both stru tures expe t two student referen e arguments. marks. Thus we an treat ea h stru ture as a fun tion! 18. we ould repla e it by sort(marks. instan eOfD).end(). Note that in the same program you might want to .8 Use in the sort fun tion Now we an repla e the line marked ****** with the line: sort(marks. instan eOfC). On the other hand.begin().end().ned an instan e of ea h stru ture as well.begin(). whi h will ause the array to be sorted by rollno.1. whi h will ause the array to be sorted by marks. marks.

rst sort the array by rollno and then by marks. in whi h ase you an make onse utive alls to sort by supplying instan eOfC .

Thus using the fun tion obje t is more general than de.rst and then instan eOfD.

instead of har arrays. 18.2 The string lass The string lass is a very onvenient lass for dealing with har data. To use the string lass you need to in lude the header . It is so onvenient.ning operator<. that you are en ouraged to use the string lass wherever possible.

q. #in lude <string> string p. // not ne essary if simple pp is in luded. q="ab ".le <string>. .r very simply. but note that it will be in luded automati ally as a part of <simple pp>. We an reate string obje ts p. string r=q.

ab '' This will print out the strings separated by ommas." << q << ".ab . will ause a whitespa e terminated sequen e of the typed hara ters to be read into p. Reading in is also simple. Noti e that you do not have to worry about the length of strings. You an print strings as you might expe t. The addition operator is de. Also you an use getline as you ould with har arrays. 298 Abhiram Ranade. We will see more variations on getline soon. in >> p. the old value is overwritten. 2011. and q and r both to "ab ". You an use assignment later as well. or allo ate memory expli itly. out << p << ". When you make an assignment. Do not distribute This will initialize p to the empty string. and not just during initialization. //prints ``." << r <<endl.

ned to mean on atenation for strings. Thus given the previous de.

r you may write p = q + r.q.nitions of p. This will respe tively set p. The operator += an be used to append. Many other useful member fun tions are de.s to "ab ab " and "ab 123". string s = q + "123".

find("ab".find(t. we should note that strings have an order de. Finally.substr(2) // substring starting at 2 going to end << p. s will be ome ab1123. // find from position 1. // indexing allowed. size_t i = p. // will print out 1123b a size_t i = p.ned. if(i == ==string::npos) out << "String: "<< p << " does not ontain "<< t << endl. Here are examples of other operations that are allowed. " << j << endl. 3 Note that if the given string is not found.find("ab"). For example.substr(1. We an use this as follows: t = "x". // find from the beginning size_t j = p.3) // starting at 1 and of length 3 << endl. s[2℄ = s[3℄. // will print out 0. else out << "String: "<< p << " ontains "<< t << " from position "<< i << endl. then the find operation returns the onstant string::npos. the member fun tions size and length both return the number of hara ters in the string. out << i << ".1). out << s.1).

e.q with the natural interpretation. . the order in whi h the strings would appear in a di tionary. i. One string is onsidered < than another if it appears earlier in the lexi ographi al order.ned on them: the lexi ographi order. Thus we may write the omparison expressions p==q or p<q or p<=q for strings p.

it need not even be numeri al! As in an array. this ondition is severely relaxed: you are allowed to use any value as the index. whi h an be a essed by supplying indi es of type indexType. To use the map template lass you need to in lude the header <map>. In a map.3 The map template lass The simplest way to think of the map lass is as a generalization of an array or a ve tor. Do not distribute 299 18. you de lare the map you want. In an array or a ve tor. This auses a map named mapname to be reated. map<indexType.valueType> mapname. Next. It stores elements of type valueType. the index is required to be an integer between 0 and the n 1 if the length of the array is n. 2011. the value of the index determines whi h element of the map is being referred to. It is required that the operator operator< be de. Abhiram Ranade.

ned for the type indexType. if the operator is not originally de. Of ourse.

you an de.ne.

However the de.ne it.

So we an de. it should be transitive and asymmetri . so our valueType is double. so our indexType ould be string. Then we an reate a map named Population.e. We would like to use the name of the ountry to a ess the element orresponding to ea h ountry. Let us take a simple example. Suppose we want to store the population of dierent ountries. whi h will store the population value (numeri ).nition should have the usual properties expe ted of a omparison operator. i. Say we store the population in billions as a unit.

21 billion Population["China"℄ = 1.35. Population["Unites States"℄ = 0.21.24. Population["Indonesia"℄ = 0.19. i. we spe ify the population of dierent ountries.31.ne our map as follows. The . map<string.double> Population.e. // population of India is 1. Population["Brazil"℄ = 0. Population["India"℄ = 1. Next we insert the information we want into the map.

for example.24. will print 0.rst line. You use an array a ess like syntax also to refer to the reated elements. the following out << Population["Indonesia"℄ << endl. and whose index is "India". reates an element whose value is 1. For example. whi h is the value stored in the element whose index is "Indonesia". You have to realize that while the statements look like array a esses super.21.

what gets stored when you write Population["India"℄ = 1. ially.21). their implementation will of ourse be very dierent. The name Population really refers to a olle tion of su h pairs.21.1. Subsequently. is the pair ("India". when we write Population["India"℄ we are ee tively saying: refer to the se ond element of the pair whose . Ee tively.

So some ode will have to exe ute to .rst element is "India".

.nd this element (Se tion 18.3. e. So a lot is happening behind the s enes when you use maps.g.2). What if you write two assignments for the same index.

2011.22. Abhiram Ranade.21. Do not distribute 300 Population["India"℄ = 1. Population["India"℄ = 1. This will have the ee t you expe t: the element reated the .

rst time around will be modi.

Say you want to print out the population of that ountry if it is present in the map. string ountry. ount( ountry)>0) out << Population[ ountry℄ << endl. else out << ountry << " not found.22. Suppose you have read in the name of a ountry into a string variable ountry.21 to 1.ed so that the value stored in it will hange from 1. You an write this as follows out << "Give the name of the ountry: ". An important operation you might want to perform on a map is to he k if the map ontains an element with a given index. if (Population. else you want to print out a message saying that the population of that ountry is not known to the program. in >> ountry. This ode should immediately follow the ode given above for de.\n".

So in this ase the . ount( ountry) would return 1 be ause we did enter the population of "India" into the map earlier. Then Population. In this ode the member fun tion ount takes as argument an index value. and returns 1 if an element with that index is present in the given map. Thus suppose the user typed in "India". in response to our request to give the name of a ountry.ning the map Population and spe ifying the population of the various ountries.

if the ountry typed in was "Britain". You may wonder what would happen if we anyway exe ute out << Population["Britain"℄ << endl.22. without assigning a value to Population["Britain"℄ earlier in the ode. The exe ution of this statement is somewhat unintuitive. will get printed. On the other hand. 1. In general suppose we have de.nal value entered. and hen e the message \Britain not found. then Population." would be printed. ount( ountry) would return 0.

ned a map map<X.Y> m. Then if we a ess m[x℄ without . and suppose x is a value of type X.

then impli itly this .rst assigning it a value.

After that the value of m[x℄ is returned. Thus in the ase of the statement out << Population["Britain"℄ << endl. the statement Population["Britain"℄=double().rst auses the statement m[x℄=Y(). i.e. an element is reated for the index x. to be exe uted.. and the element stores the value Y() obtained by alling the default onstru tor of lass Y. is .

Hen e this unknown value would get printed. .rst exe uted. So the map will now ontain an element of unknown value but having the index "Britain". The onstru tor for the type double unfortunately does not initialize the value.

the program had to print marks for any student name was presented to it.1 Marks display variation 3 In the third variation. Abhiram Ranade. To make the problem more interesting. Further assume that the names are given in a .3. Do not distribute 301 18. Physi s. and after all data is entered. we had student names being entered. we will assume that for ea h student we have the marks in Mathemati s. and a map to store marks of students. we an use strings to represent student names. Clearly. and Sanskrit. 2011.

95. 80 Vibhavari Shirurkar. 85. A. A. 99. 75 i. 90. Fair. 80. the .e. 95.le with lines su h as the following. 90 Ni olas Bourbaki.

le will ontain a line for ea h student with the name appearing .

This format. in whi h ea h line of the .rst. following whi h 3 numbers would respe tively give the marks in the dierent subje ts. The numbers are also separated by ommas. su eeded by a omma.

or the \ omma separated values" format. To store the marks. The marks will be stored in a map.marks> mark_map. We will use a string to store the student name. }. Say our . map<string. is often alled the CSV format. we will use a stru ture.le ontains values separated by ommas. math. whose index will be the name of the student given as a string. stru t marks{ double s ien e. sanskrit.

txt.txt"). // needs #in lude <fstream> Next we dis uss how to read values from a .le ontaining the marks is named marks. Then we an de lare it in our program as ifstream infile("marks.

string stringname. . For this we an use a form of getline fun tion whi h allows a delimiter hara ter to be given. instream is the name of the input stream from whi h data is being read. The signature for this is: istream& getline(istream& instream. The hara ter delim is dis arded.'. and the data read till then is stored into string stringname. getline(infile.'). Thus. data is read from the stream instream until the hara ter delim is found. Thus. we an read the name of a student by exe uting something like: string name. The parameter stringname is the name of a string.le in the CSV format. and delim is the hara ter that delimits the read. har delim) In this.name.

2011. 302 Abhiram Ranade. Do not distribute Used with the .

Fair". In the .le above. Of ourse. from whi h we read into the variable mmath. Subsequently if we exe ute getline(infile. Similarly. the string name would then hold the string "85". again.'.name. stringstream (name) >> mmath. A.'). this would ause the string name to be onverted into a stringstream. we would like to onvert this to a double. so we an use a stringstream: double mmath. the other data an be read. Figure 18. // need #in lude <sstream> As you know. this statement will ause name to get the value \A.1 ontains the entire program based on these ideas. in luding the spa es inside it.

rst part. the .

The .le is read into the map mark map.

the name.rst 3 values on ea h line. So they are used as dis ussed above. The last . the marks in math and the marks in s ien e are omma separated.

. it must be dis arded. The standard library allows some generi pro essing of ontainers. and we will glan e at some of them shortly. or maps. It is intended to be used in a manner analogous to the use of an (a tual) pointer in the following ode whi h applies a fun tion f to all the elements of an array.e.1. If a name is present in the map.4 Containers and Iterators The lasses ve tor and map are onsidered to be ontainer lasses. whi h in turn must be smaller than the indi es of the elements in the right subtree. they are used to hold one or more elements.e. 2 18. or even strings. i. The ordering rule is that all pairs in the left subtree must have index smaller than that at the root. Note that when reading using the operator >>.value) pairs onstituting a map are stored using binary sear h trees like those in Se tion 17. In the se ond part. the program repeatedly reads the names of students. Aptr<A+10. This is a omplished using an iterator. An iterator an be thought of as a generalized pointer to an element in a ontainer.eld is not omma separated. Thus making an a ess su h as Population[ ountry℄ happens fairly fast. then the orresponding marks are printed. so it an be read dire tly. the end of line hara ter is not read. There are other ontainers as well in the Standard Library. For this. in time proportional to log n. So before the next line is to be read. i. where n is the number of ountries for whi h data is stored in the map.2 Time to a ess a map The (index.2.3. Even a string is thought of as a ontainer be ause it ontains sets of hara ters. advan ed te hniques are used to ensure that the tree height is always logarithmi in the number of pairs stored in it. be they ve tors. it is ne essary to be able to refer to the elements of the ontainer in a uniform manner. Further. int A[10℄ int* Aptr for(Aptr = A. Aptr++) f(*Aptr). 18.

not omma terminated getline(infile. getline(infile.'.')){ string s. Do not distribute #in lude #in lude #in lude #in lude <simple pp> <fstream> <sstream> <map> stru t marks{ double s ien e. Abhiram Ranade. stringstream (s) >> m.'. int main(){ ifstream infile("students.s. // store the stru ture into the map while(getline( in. map<string.\n". math.math << " " << mark_map[name℄.'. sanskrit.math. else out << "Invalid name. 2011.s). while(getline(infile. string name. stringstream (s) >> m.name)){ if(mark_map.'). getline(infile.txt").sanskrit << endl. } Figure 18.marks> mark_map. // dis ard the end of the line hara ter } } mark_map[name℄ = m. ount(name)>0) out << mark_map[name℄. // read dire tly.sanskrit.').s. infile >> m.s ien e.name.s ien e << " " << mark_map[name℄.1: Program for Marks display variation 3 303 . }. marks m.

Abhiram Ranade. and then in rement it so that it points to su essive elements. 2011. In ea h iteration we dereferen e it and then apply the fun tion f to it. Do not distribute 304 In this ode we initialize the (a tual) pointer Aptr to point to the zeroth element of A. Impli it in this ode is the idea that the elements are ordered in a unique manner: spe i.

we will have an iterator whi h will abstra tly point to elements of the ontainer. Analogous to the a tual pointer Aptr. Now we see how we an write analogous ode for ontainers. an iterator for a map an be de. and whi h we an step through as the exe ution pro eeds. In general. ally the elements are onsidered in the order in whi h they are stored in memory.

Y>::iterator.Y> m. Next we need to say how to set it to \point" to the .Y>::iterator mi. map<X.ned as follows. Here mi is the iterator. map<X. and its type is map<X.

rst element in the map. For this we . and then how to step it through the elements.

rst need to .

e. i.x an ordering of the elements stored in the ontainer. the elements are onsidered ordered a ording to the index. the . For ve tors and maps.

The member fun tion begin on the ontainer returns an iterator value that abstra tly point to this .rst element is the element with the smallest index.

begin().rst element. Thus we an initialize our iterator by writing: mi = m. and by using the operator ++. For this the member fun tion end on the ontainer is de. Finally. the iterator an be made to point to the next element in the order. An iterator supports two operations: by dereferen ing you get to the element abstra tly pointed to by the iterator. to determine when the iterations should stop we need to know when the iterator has been in remented beyond the last element in the order.

Suppose we wish to merely print all the elements in a ontainer. Then here is how this an be done using iterators. just as the address A+10 in the example above points beyond the last element of the array. .ned to abstra tly point beyond the last element.

Sin e we onsider an iterator to be a pointer.3. Pi != Population. for(ve tor<float>::iterator mi = marks. When we dereferen e a map iterator.begin().rst for the ontainer marks of Se tion 18. mi != marks. The ode for map ontainers is similar. Here is how we an print out the map Population of Se tion 18. with data members first and se ond whi h hold the index and the value respe tively.end().4.end().begin(). whi h is an (index. The pair that we get is a (template) stru t. ++Pi) out << Pi->first <<": " << Pi->se ond << endl. the stru t elements an be a essed using the operator ->.1. ++mi) out << *mi << endl. .double>::iterator Pi = Population. for(map<string.value) pair. we get an element of the map.

map<string. You an delete the element pointed to by an iterator by using the erase fun tion as follows. For example. // deleting an element The .2 Inserting and deleting ve tor elements Iterators an be used with ve tors for inserting and deleting elements. But you dont need to worry about all this.1 Finding and deleting map elements Iterators are spe ially important for the map lass. 305 Abhiram Ranade. 18.end().begin() + 5. ve tor<int>::iterator vi = v.100). Thus to see if the value "Britain" is stored in the map Population. v.erase(Pi). these operators are given to you appropriately overloaded. We an use the find operation on iterators to get to an (abstra t) pointer to an element whi h has a given index value.find("Britain"). i<10. So to see if "Britain" is present and print its population we an write: map<string. 2011. for(int i=0. then Pi would take the value Population. you an onsider iterators to be abstra tions of pointers for the purpose of using them.double>::iterator Pi = Population. Do not distribute Similar ode an be written for the string lass.find("Britain").push_ba k(i*10). 18.erase(vi). Population.4. Note that the dereferen ing operator * or the in rementation ++ should not be understood literally. // inserting into a ve tor vi = v. If "Britain" is not present. if(Pi != Population. i++) v. we an write: map<string. we ould write ve tor<int> v. v.int>::iterator Pi = Population. This would remove the entry for Indonesia.begin()+7.find("Indonesia").4.insert(vi.end()) out << Pi->first << " has population "<<Pi->se ond << endl.int>::iterator Pi = Population.

Then 100 is inserted at that position. 70. 90. The size of the ve tor of ourse in reases by one. 80. i.e.rst two statements respe tively de lare a ve tor v and set it to ontain the elements 0. the elements in the positions seventh onwards being moved down one position. the element ontaining 70. 30. After that we set vi to point to the . 40. 50. 60. The third statement auses vi to point to the seventh element of v. 20. 10.

100. 90. 10. 40. 30. 70.fth element. Thus at the end the ve tor v would ontain the elements 0. 20. This auses the subsequent elements to be moved up one position. 80. . Then that element would be deleted. 60.

2011. Do not distribute 306 18. For example. This supports operations for inserting elements and subsequently . The ontainer queue allows insertions at the ba k and removal from the front. An important ontainer is the priority queue. You an insert elements arbitrarily. however.5 Other ontainers in the standard library The standard library has several other ontainers whi h are very useful. the ontainer deque is a double ended queue. while the ontainer sta k requires that insertions and removals both be done from the same end. Abhiram Ranade. An interesting ontainer is the set. We dis uss and use priority queues in Chapter 21. into whi h you may insert or remove elements from the front as well as the ba k. when removing elements. you always get the smallest element inserted till then.

nding them. The elements are required to have operator< de.

The elements are ordered a ording to the operator< order de.ned on them. just as a map was stored in a binary sear h tree. and this order is used for storing the elements in a binary sear h tree.

forwardIterator last. 18.4. onst T& value_to_sear h).ned on them. You should onsult various standard library referen es on the web to get details. The algorithm olle tion in SL also ontains a binary sear h fun tion for performing binary sear h on sorted ontainers su h as ve tors. Here the region of the ontainer between first (in lusive) and last (ex lusive) is sear hed to . The signature of this fun tion is bool binary_sear h(ForwardIterator first. we really dont need to expli itly sort them.6 Exer ises 1. and will get printed in this order if printed using iterators as in Se tion 18. This des ription is of ourse very sket hy. So if we store elements in a set.

using just ve tors rather than maps. Write a program that prints out all positions of the o urren es of one string pattern inside another string text. The type of the element stored in the ontainer must be T. The fun tion binary sear h is guaranteed to exe ute in logarithmi time when used with ve tor ontainers. 3. The fun tional obje t must ee tively behave like the < operator. even if the degree of a polynomial is n.e. An additional argument. Exploit this order to get eÆ ient implementations. Use this to implement variation 3 of the marks display program.e. store the pair (i. it might be more eÆ ient to store only the non-zero oeÆ ients. Note that intertors on maps will go through stored pairs in lexi ographi al order. Use a map to store su h pairs. i.e. In su h ase.nd an element equal to value to sear h. many of the powers might have oeÆ ient 0. Instead. there may be far fewer terms in the polynomial. Polynomials are often sparse. ai) if the oeÆ ient ai of xi is non-zero. it may be wasteful to allo ate an array or ve tor of size n + 1 to store a polynomial. a fun tional obje t is also allowed. 2. . i. Write fun tions to add and multiply polynomials. i.

and then prints out the marks obtained given the name of a student and the name of the subje t for whi h the marks are requested. of whi h ea h student might have studied and got marks in some. . 2011. Abhiram Ranade. Suppose for ea h student we know the marks in several subje ts. You are expe ted to use a map to store the data for all students. Write a program whi h reads in the marks a student has obtained in dierent subje ts. The total number of subje ts might be very large. Do not distribute 307 4. and a map for ea h student in whi h to store the marks for the dierent subje ts taken by the student.

We will see an example of this idea in Se tion 19. the programmer may hange some of the inherited fun tion members. B. the lass B gets (\inherits") all the data members and ordinary fun tion members of A. As you might suspe t. B is said to inherit from A. Suppose lass A represents a real-life entity A. Inheritan e an play a entral role in the design of omplex programs. Created this way. The goal in these examples is to merely reate a new lass B whi h is similar but not identi al to a given lass A. is derived from A.g. Often. E. The most ommon (and re ommended!) use of inheritan e is in the following setting. or obtained by extending A. this is a onvenient way to reate new lasses. The designation pro ess does not require any ode from A to be opied to B. Of ourse. The key idea is: you an reate a lass B by designating it to be derived from another lass A. savings a ounts and urrent a ounts. It is likewise ustomary to say that A is a super lass of B.4. Furthermore.Chapter 19 Inheritan e Inheritan e is one of the most important notions in obje t oriented programming. a ounts) by a lass.C. and perhaps lasses E. e. or base lass of B or sometimes the parent lass of B. In su h a ase. and more substantial examples in the next hapter. We will inherit the ommon part and separately de. Then B an often be represented using a lass B derived from lass A. It is ustomary to say that lass B is a sub lass of lass A. For example. a program might be on erned with bank a ounts. F are said to onstitute an inheritan e heirar hy. a program deals with ategories of obje ts. C. and the programmer may give additional members to B. and sub ategories (savings a ounts and urrent a ounts) by sub lasses. In su h ases it turns out to be useful to represent a ategory (e. and these may be divided into dierent types of a ounts. B need not be an exa t repli a of A.F inheriting from B. avoiding multiple opies of ode is an important motivation for inheritan e. whi h are divided into sub ategories. An important point to be noted is that the pro ess of inheritan e does not hange the super lass in any way. Suppose another real-life entity B is a spe ialized version of A. And of ourse. So we begin by onsidering a few simple examples.g.D inheriting from A. D. in fa t. In this hapter we are on erned more with the me hani s of inheritan e. We an have several lasses say B. the lasses A.

1 1 This is as in real life: inheritan e ae ts the hildren but not the parents. this requires A to be written in a manner that will fa ilitate the inheritan e.ne in B the part that is unique to B. we an design lasses so that it is possible to reate sub lasses from them later. Of ourse. 308 . But with some foresight.

1 Example 1 In our . Abhiram Ranade. Do not distribute 309 19. 2011.

turn. ex ept that the turtle will keep a ount of how mu h distan e it has overed. Here is how we an de.rst example. So a meteredTurtle will be able to move forward. hange olours et . just like a Turtle. we will design a lass meteredTurtle whi h is exa tly like the lass Turtle. but in addition it will have an additional member fun tion distan eCovered whi h will return the total distan e overed till then.

} }.ne meteredTurtle. } void forward(float d){ distan e += abs(d). In order to inherit from a lass. the lass must be de. // Turtle::forward(d). publi : meteredTurtle(){ distan e = 0. } float distan eCovered(){ return distan e. #in lude <simple pp> lass meteredTurtle : publi Turtle{ float distan e.

the lass Turtle must be de. Thus to inherit from Turtle.ned in the urrent ontext.

ned. The de.

nition of the Turtle lass (i. the header.e.

The . Hen e we have emphasized the in lusion of simple pp above.le Turtle.h) gets in luded when we in lude simple pp.

rst line of the de.

This says that the lass meteredTurtle is being de.nition has a new part \: publi Turtle".

but in this book unless spe i. C++ allows inheritan e to be invoked in dierent ways. We will dis uss other kinds of inheritan e later.ned by inheriting from the lass Turtle. the most ommon of these ways is publi .

The body of the de.ed otherwise we mean publi inheritan e when we speak of inheritan e.

Thus the .nition merely states what is dierent in the sub lass as ompared to the super lass.

rst line inside our meteredTurtle de.

nition de.

The de. over and above all the members that Turtle (instan es) will have.nes a private member distan e. This will be an additional data member that meteredTurtle (instan es) have.

nition of meteredTurtle also ontains three member fun tion de.

These will extend the member fun tions available to instan es of meteredTurtle. The .nitions.

rst member fun tion is a onstru tor for the new lass. so you must de. Note that onstru tors and destru tors are not inherited.

You may wonder how the inherited members of meteredTurtle get initialized. as we will see later. to 0.ne them afresh for ea h sub lass. the lass Turtle ontains many data members whi h are used to hold information about the turtle su h as its position on the s reen. and so on. This is meant to signify that at the beginning the turtle has not travelled any distan e. distan e. The onstru tor for meteredTurtle merely initializes the new member. olour. Indeed. These get initialized .

Do not distribute 310 be ause of the following rule of C++: before exe uting the ode for a onstru tor of a lass. Thus before setting distan e to 0. 2011. and you an still be assured that the inherited members will be initialized! Next we have a de. initialize the inherited members by alling the onstru tor of its super lass. whi h auses the inherited members to be initialized. Noti e that this is very onvenient: as a programmer you do not even need to know what the lass is inheriting. a all is impli itly made to the default onstru tor of Turtle. Abhiram Ranade.

Note .nition of the member fun tion forward.

rst that Turtle already has a forward member fun tion. So if we de.

ne forward again. then it means that for meteredTurtle obje ts. the new de.

nition is to be used rather than the one that would have been inherited from Turtle. In the new de.

the value by whi h we move forward is .nition.

The forward fun tion from the Turtle lass auses the turtle to move forward on the s reen. Here is a main program that uses the above de. So this is what the last statement does. As you see. we take the absolute value. This alls the forward fun tion from the Turtle lass.rst added to distan e. This fun tion an be used only with instan es of meteredTurtle and not with instan es of Turtle. and not present in Turtle. The last fun tion distan eCovered() is new. this fun tion merely returns the value of the data member distan e. Sin e the argument to forward an be negative. The last statement in this fun tion is noteworthy: Turtle::forward(d).

main_program{ initCanvas("Metered turtle"). For the .Turtle::forward(100). mt. mt. meteredTurtle mt.forward(100).left(90).nition. turning right 90 degrees between the moves. mt. } mt. mt.distan eCovered() << endl. out << mt. We reate the metered turtle mt and then move it forward by 100 pixels 3 times.forward(100).left(90).

and will also in rement the distan e member in mt. The third time we have used Turtle::forward. by the time ontrol arrives at the last statement. in pra ti e you are expe ted to use only forward with meteredTurtle and not Turtle::forward. Hen e. This will move mt forward.rst two moves our ode uses just forward. distan e will have got in reased to only 200. Of ourse. whi h will get printed.2 Example 2 The se ond example we onsider is for the V3 lass as de. 19. as a result the new forward fun tion gets used. Note that this will not in rement distan e. this auses the method from the Turtle lass to be used. if you want the distan eCovered fun tion to orre tly report the distan e overed.

Remember. .ned in Se tion 14.8. Suppose we wish to add a fun tion to this lass whi h omputes the ve tor dot produ t.

You might ask why not just modify the V3 lass ode and add our new member fun tion. Do not distribute given two ve tors (a. f ) their dot produ t is the number ad + be + f . ) and (d. 2011. e. 311 Abhiram Ranade. you have only been given the obje t module and the header . b. Suppose you do not have the sour e program.

inheritan e provides an elegant way to extend the V3 lass. You simply de. In this ase.le.

The myV3 lass will inherit all other fun tions and will also be able to perform dot produ ts. and into that you add the new dot produ t fun tion.ne a lass myV3 whi h inherits from V3. Here is a de.

y.r). For this we simply write the all to the onstru tor after the parameter list and before the body.h" lass myV3 : publi V3{ publi : myV3(double p=0.q. Thus the inherited members are initialized using the all V3(p.r){ // onstru tor } double operator*(myV3 &v){ // dot produ t return getx()*v. So in this ase. Thus in our example.5. out << X*Y << endl.z respe tively to get the values of p.getx() + gety()*v. int main(){ myV3 X(1. Y(4. } }. } Our new lass does not have any new data members.q.getz().q. following a \:".6). This auses the inherited members (Se tion 14. It is possible to spe ify whi h V3 onstru tor to use. double q=0. #in lude "V3. the text \: V3(p.3). double r=0) : V3(p.nition of myV3 and a small program to test it.length() << endl. We noted in the previous se tion that the onstru tor of the super lass is impli itly exe uted to initialize the inherited members before the before the onstru tor of the sub lass is exe uted.q. and what arguments to use for the all. but just a onstru tor and the fun tion to ompute the dot produ t.2.8) x. We will see this form in more detail in the next se tion. a onstru tor of the V3 lass would get exe uted.r.r)" does this. out <<X. Then we have the de.gety() + getz()*v.

z. The reason for this will also be seen in the next se tion. p p The main program will . Note that this uses the a essor fun tions getx. gety.y. getz rather than dire tly a ess the data members x.nition of the dot produ t as the operator *.

rst print the length of X. 2 19. 1 + 2 + 3 = 14. using the new member fun tion operator*. using the inherited fun tion length. Then it will print the dot produ t. 1 4 + 2 5 + 3 6 = 32.3 General prin iples 2 2 In general we an de.

ne a lass B an as a sub lass of a lass A. by writing: .

Indeed. 2011. The body of the de. Do not distribute 312 lass B : publi A { // how B is different from A } This will reate a lass B whi h will have all data members and ordinary fun tion members of A. we an assume that an obje t of lass B will ontain inside it an obje t of lass A. We will all this inner obje t the ore obje t. Abhiram Ranade.

nition will des ribe additional data members. and additional member fun tions that B has. The body may ontain rede.

suppose the body ontains a de.nitions of ore member fun tions as well. For example.

i. a fun tion already de.e.nition of f. whi h is a ore member fun tion.

ned in A. the new de. In su h a ase.

The new de.nition is to be used with instan es of B.

nition is said to override the old de.

nition. and will be used for obje ts of lass B. The de.

nition of f from A will ontinue to be used for obje ts of lass A. Instan es of lass B an also use the old de.

Instead of just using the name f of the fun tion. a slightly involved syntax is needed.nition from A if ne essary. to do that. we must write A::f. Only. Note that the lass A must itself be de.

ned when we de.

This is typi ally a omplised by in luding the header .ne B.

i.le of A. Although the ea h obje t of lass B ontains inside it an obje t of lass A.e. the ore obje t. the de.

Case 1: m is a publi member of A: In this ase.1 A ess rules and prote ted members Suppose that m is a data or fun tion member of A and b is an instan e of B. m an be a essed inside the de.3. Then the manner in whi h the member m of instan e b an be a essed is determined by the following rules. In other words. How data and fun tion members of A an be be used in lass B is determined by the following rules.nition of B may not have a ess to all members of A. we an onsider m to be a publi member of B as well. 19.

as well as outside the de.nition of B.

nition of B. Then inside the de.

and outside the de.nition of B we an refer to this member as just m.

Case 2: m is a private member of A: Then m annot be a essed even inside the de.nition of B we an refer to it as b.m.

private members are a essible only inside the de. In other words. And of ourse it annot be a essed outside.nition of B.

nition of the lass in whi h the member was de.

y. getz to a ess private members x. the ode in B an refer to f. and hen e it will indire tly refer to m. The sub lass instan es annot dire tly a ess private members of the super lass. There might well be a publi or prote ted (see below) member fun tion f of A whi h refers to m. This is not to say that private members of the super lass are useless.z of V3 while de. We saw an example of this when we used a essor fun tions getx. Now. gety.ned (and its friend lasses).

2.ning myV3 in Se tion 19. Case 3: m is a \prote ted" member of A: We have not de.

ned the notion of prote ted yet. So what we give is the de.

A) an be a essed inside the de.nition.g. A prote ted member of a lass (e.

but not outside.g. . Here is a ode snippet that gives an example of the above rules.nition of an inheriting lass (e. B).

out << get_q() << endl. and an hen e not be a essed in the de. prote ted: int r. r=z. Compiler errors 1 and 2 are be ause q is private in A. // ompile time error 1 out << r << endl. int z){p=x.p b. q=y. out << q << endl. you will get the 4 ompiler errors as marked.3).2.init(1. lass B: publi A{ publi : void print(){ out << p << endl. } out << << << << << b. b. } }. int y.print(). int get_q(){return q.} private: int q. int main(){ B b.q b. (with #in lude <simple pp> at the top).} }.r b. b. 2011. Abhiram Ranade. Do not distribute 313 lass A{ publi : int p.get_q() endl. // ompile time error 2 // ompile time error 3 // ompile time error 4 If you ompile this ode. void init(int x.

nition of B. Compiler errors 3 and 4 are be ause r and get q are prote ted in A. or in main. and hen e annot be used outside of the de.

nition of A or of any sub lass of A. Indeed you will see that r and get q() an be used .

ne inside the de.

nition of B. you will see that the ode will ompile . sin e B is a sub lass of A. On e the oending lines are removed.

2 as a result of b. whi h is possible be ause init gets inherited from A.ne. and 1 as a result of the last print statement in main.print(). and print 1.3.init. Note that in the se ond line of main we have used b. .

Then we ould write an alternate onstru tor for meteredTurtle as follows. An instan e of B also ontains new members. these are onstru ted inside the body of the onstru tor. the default onstru tor of A gets alled. 19.4). } With this onstru tor. The data members inherited from A? These would be destroyed by an impli it all that would get made to the destru tor of A at the end of the exe ution of the all to the destru tor of B. Consider the following ode. B( onstru tor arguments) : all-to- onstru tor-of-A { // ode whi h onstru ts new members of B } The all-to- onstru tor-of-A merely onstru ts the ore obje t (of lass A) ontained inside the instan e of B being reated. lass Animal{ publi : . This is very similar to what happens for nested stru tures (Se tion 14. In Se tion 19. the metered turtle would be reated at position (x. the ode of the super lass be omes polymorphi be ause it an be exe uted for obje ts of the super lass and also the sub lass. A onstru tor for B has the following general form. whi h we explore next. in reverse order of reation. You should not expli itly make a all to the destru tor of A from inside the destru tor of B! The general rule is: destru tion happens automati ally. In the exer ises you will experiment with ode whi h will illustrate these ideas. double y) : Turtle(x. Abhiram Ranade. Suppose now that we had an alternate onstru tor for Turtle whi h took arguments x. Do not distribute 314 19. meteredTurtle(double x.3.2 Constru tors and destru tors Suppose that lass B is a sub lass of lass A. Clearly. in the general setting. We now dis uss destru tors.y) on the s reen.1 you saw an example in whi h the default onstru tor of Turtle got used for reating a meteredTurtle. As before suppose we have a lass B whi h inherits from lass A. 2011. The part : all-to- onstru tor-of-A is optional.4. on e we use inheritan e.3 Polymorphism and virtual fun tions A pie e of ode is said to be polymorphi if it an be exe uted for variables of more than one type. The onstru tor of A is alled before the body of the onstru tor of B is exe uted. or more than one lass.3. Then the destru tor for lass B should be used to destroy the new data members introdu ed in B that were not present in A.y giving the initial position for the turtle. If it is omitted.y) { distan e = 0. This raises some subtle questions.

a. Will it be the name in Animal or in Mammal? The answer turns out to be the name in Animal.whoAmI(). int main(){ Animal a.whoAmI(). Mammal b. b. } Exe uting a. Abhiram Ranade.whoAmI() will learly ause \Animal" to be printed out. There is a natural reason for this. More interesting is the exe ution of b. What should it print? The all b. When lass Animal is de. \Animal" will be printed.whoAmI().whoAmI() is to the inherited member fun tion whoAmI in the super lass Animal. and thus in this ase. } lass Mammal: publi Animal{ publi : string name(){ return "Mammal". 2011. but the question is whi h name. } string name(){ return "Animal". That fun tion whoAmI alls name. Do not distribute }. } }. 315 void whoAmI(){ out << name() << endl.

the referen e to name in the body of A::whoAmI is understood by C++ to mean the name in Animal itself.ned. This understanding is not hanged when Mammal is de.

But you might suppose that it should be useful if the name in Mammal gets used instead. C++ provides a way to a omplish it: add a single keyword virtual to the de.ned.

nition of name in Animal. Thus the lass would be de.

} }. This keyword says that the de. } virtual string name(){ // note the added keyword virtual return "Animal".ned as: lass Animal{ publi : void whoAmI(){ out << name() << endl.

.nition of name should not be treated as a unique.

nal de.

nition. that de. and if so. It is possible that name might be over-ridden in a sub lass.

When we all b.whoAmI().nition of name whi h is most appropriate (most derived!) for the obje t on whi h the all is made should be onsidered. the most appropriate de.

nition for name is the one in Mammal. So that de. sin e b is of type Mammal.

and our ode will now indeed print \Mammal".nition gets used. Note that a.whoAmI() will ontinue to print \Animal". .

Suppose B is a sub lass of A. where A is a lass. Suppose now that f is a member fun tion in A whi h has been overridden in B.}. We will see its utility immediately in Se tion 19. B b. If we de lared f to be virtual. whi h we explain next. aptr = &b.. Then we an store addresses of instan es of A as well as of B (or even of instan es of sub lasses of B and so on) in aptr. Suppose that f does not have any parameters. In other words. Abhiram Ranade.. lass A{ . is an extremely important part of inheritan e.. then the ode for f de. Whi h version of f will get exe uted? The situation is analogous to the previous se tion. This feature. A* aptr. the following ode is legal. }. The pointer variable aptr is said to be polymorphi be ause it an ontain pointers to obje ts of more than one lass. Then suppose we exe ute: aptr->f().4 Suppose that aptr is a variable of type A*.4 Polymorphism and pointers C++ also allows polymorphi pointers. lass B : publi A{. Do not distribute 316 19..3. 2011.

But you will perhaps observe that for most verbs. and prints out its past tense. A simple implementation would be to store every verb and its past tense as strings in memory. for regular verbs we ould simply atta h \ed" when asked. given \play". and so on. \eat" whi h do not follow this rule ould be onsidered irregular. the program must print \wrote". 19. Given the verb. This an be programmed quite ni ely using inheritan e. \look". \speak". we an then print out the orresponding past tense. the past tense is obtained simply by adding a suÆx \ed". given \write". \walk". as is the ase for the verbs \play". Verbs su h as \be". Otherwise the ode from A will get exe uted. We de. the program must print \played".ned in B will get exe uted. Thus it makes sense to store the past tense form expli itly only for irregular verbs. Thus. We may onsider these verbs to be regular.4 Example 3 Suppose you wish to write a program that takes as input a verb from the English language.

ne a lass verb that represents all verbs. it onsists of sub lasses regular and irregular respe tively. The de.

nition of verb ontains information whi h is ommon to all verbs. The de.

nition of regular adds in the extra information needed for regular verbs. and similarly the de.

lass verb{ prote ted: string root. publi : .nition of irregular.

} virtual string past_tense(){return ""}. Do not distribute }. Abhiram Ranade. 2011. 317 string getRoot(){return root. We have de. The member root will store the verb itself.

string p){ root = rt.ned the member fun tion past tense to be virtual. pt = p. For now it returns the empty string. } string past_tense(){return pt.past tense() would return \was". we would get the string "played" as the result.} }."was"). // past tense of the verb publi : irregular(string rt. lass irregular : publi verb{ string pt. Similarly irregular v2("be". sin e we expe t to override it in the sub lasses. But this is not important. Thus. lass regular : publi verb{ publi : regular(string rt){ root = rt. And of ourse v2. would reate an instan e v2 to represent the verb \be".} }.past tense(). We now see how the above de. to reate an instan e v1 that represents the verb \play" we would just write regular v1("play"). } string past_tense(){return root + "ed". After this if we wrote v1. The sub lasses regular and irregular are as you might expe t.

we use a ve tor. Clearly. we an de. However. We annot have a single ve tor storing both regular and irregular verbs. For this. we will need to somehow store the information about verbs.nitions an be used to write a main program that returns the past tense of verbs.

push_ba k(new regular("play")). V. .ne a ve tor of pointers to verb in whi h we an store pointers to irregular as well as regular obje ts. Thus the program is as follows.push_ba k(new regular("wat h")). int main(){ ve tor<verb*> V. V.

Our need was to represent the ategory of verbs whi h onsisted of mutually disjoint sub- ategories of irregular and regular verbs.size().size()) out << "Not found. } if(i == V. 19.4. without worrying about whether the obje ts are of type regular or irregular. whi h the sender need not know. In this ase we print "Not found. The virtual fun tion past tense is an ex ellent example of this. e. This is a very powerful idea in obje t oriented programming. 19.g. but it is not aestheti ally pleasing that we should .push_ba k(new irregular("go". virtual fun tion invo ation is analogous to sending a message. Finally. As you know. i<V. we enter a loop in whi h we read in a query from the user. Do not distribute 318 V. V. This idea works.size(). The message is re eived by the obje t and the obje t a ts upon it in its own way. but we did this be ause we expe ted that the verb lass would never be used dire tly. we print its past tense.\n".1 The message metaphor It is often metaphori ally said that with inheritan e."."went")). Be ause past tense is virtual. 2. Note that if the for loop ends with i taking the value V. } We begin by reating the ve tor V. A number of points are to be noted regarding the use of inheritan e in this example. only its sub lasses would be used in whi h the fun tion would get overridden. Returning an empty string does not make sense. for(i=0. the while loop will terminate when in ends. Abhiram Ranade. while( in >> query){ size_t i.push_ba k(new irregular("be". 2011. if the user types ontrol-d. We then reate instan es of regular and irregular verbs on the heap. This is a very standard situation in whi h inheritan e an be used. it must be the ase that no entry in V had its root equal to the query. We an invoke the operation past tense on obje ts pointed to by elements of V. If so. } string query. The ve tor V is polymorphi : it an ontain pointers to obje ts of type irregular as well as of type regular.5 Abstra t Classes You will note that we return the empty string in the past tense fun tion in verb. he k if it is present in our ve tor V. and store pointers to them in onse utive elements of V. 1. i++) if (V[i℄->getRoot() == query){ out << V[i℄->past_tense() << endl. break. the orre t ode gets exe uted."was")).

Do not distribute need to supply an implementation of past tense in verb expe ting fully well that it will not get used. and not supply any implementation at all. 2011. whenever an implementation is not supplied. Unfortunately. 319 Abhiram Ranade. One possibility is to only de lare the member fun tion past tense in verb. the ompiler expe ts to .

nd it somewhere. in some other .

the ompiler expe ts that somewhere else we would supply the implementation string verb::past_tense(){ // implementation } If su h a de. In other words.le perhaps.

then the lass verb would be ome abstra t. if we assign past tense to 0 in verb. You may think of 0 as representing the NULL pointer. So in our ase... Then we annot reate an instan e of A! This is be ause for that instan e we would not know how to apply the fun tion f. We would not be able to reate instan es of it. This is done by suÆxing the phrase \= 0" following the de laration. lasses whi h annot be instantiated are said to be abstra t. In C++. What we need is a way to tell the ompiler that we do not at all intend to supply an implementation of past tense for the verb lass. and hen e ee tively indi ating that there is no implementation.nition is not given the ompiler or the linker will produ e an error message. publi : virtual string past_tense() = 0. Thus we would write lass verb{ .. There is an important onsequen e to assigning a fun tion to 0. But this is . } Writing \= 0" following the de laration of a member fun tion tells the ompiler that we do not intend to at all supply an implementation for the fun tion. Suppose a lass A ontains a member fun tion f assigned to 0. the only way of making a lass abstra t is to assign one of its member fun tions to 0. . Indeed..

instead we expe t them to instantiate either regular or irregular. we indeed would not like users to instantiate verb. 2 19.6 Exer ises 1.ne. The * operator we de.

How will you onvert it to mypoly? Write a onstru tor that takes a poly obje t as argument and returns a mypoly obje t representing the same polynomial. then ee tively we have ensured that the lass annot be instantiated. but the result will be of type poly.ned for poly is inherited in mypoly. Using this you should be able to write: If we make the onstru tor of a lass private and there are no member fun tions that use the onstru tor. This will allow two obje ts of type mypoly to be multiplied. 2 . But te hni ally su h lasses are not onsidered to be abstra t.

int main(){ C . 4.} }.b. Write the past tense generation program using just two lasses. Also add the right and left methods.} ~C(){ out << "Destru tor(C). Do not distribute 320 mypoly a.} ~B(){ out << "Destru tor(B). 2. a verb lass and an irregular lass. lass A{ publi : A(){ out << "Constru tor(A). Add a method derivative whi h should return a polynomial whi h is the derivative of the given polynomial. Abhiram Ranade. 2011.\n".} ~A(){ out << "Destru tor(A). lass C: publi B{ publi : C(){ out << "Constru tor(C). 3.\n". a. } 5. and an irregular as an instan e of irregular. Also add a method root(float x) whi h returns the root of the polynomial obtained by starting at x and using the Newton-Rhapson method.\n".} }. A regular verb should be reated as an instan e of verb.\n". . lass B: publi A{ publi : B(){ out << "Constru tor(B).} }. What do you think will happen when you exe ute the program given below? Run it and he k if you are right.\n". Modify the forward method in Turtle su h that the turtle moves slowly.\n".read(). Also add the penUp and penDown methods.read(). mypoly = mypoly(a*b). b.

Its .Chapter 20 Inheritan e based design Inheritan e is often very useful in designing large omplex programs.

There are many approa hes to designing a large program. and then in the rest of the hapter we will see some examples. A lassi al approa h requires that we . We will dis uss these next. But there are some related advantages whi h have to do with the management of the program development pro ess.rst advantage we have already dis ussed: inheritan e is onvenient in representing ategories and sub ategories.

As we have dis ussed. users will inevitably ask that it be enhan ed with more features. Also. the whole point of inheritan e is to build new lasses out of old. programs will have a long lifetime in whi h the requirements will evolve. So the modern approa hes stress the need to design programs su h that it is easy to hange them. if a program works beautifully. More modern approa hes instead a knowledge/allow for the possibility that requirements may not be understood unless one has built a few versions of the program.rst make a omplete study of the program requirements. and only thereafter start writing the program. In any ase. Even if the requirements are well understood and . and this idea will surely ome in useful when requirements hange.

It greatly helps if the program an be designed as a olle tion of mostly independent fun tions or lasses whi h intera t with ea h other in a limited.xed (at least for that time in the program development pro ess). designing a large program is tri ky. learly de.

inheritan e based designs have mu h to oer in this regard also. to write professional programs you will not use bare C++ (or any other programming language). whi h will enable you to de. Finally. We will rewrite it using inheritan e. But it also has another advantage: dierent programmers an work on the dierent parts simultaneously. but will start from a olle tion of fun tions and lasses whi h have been already built by others (for use in other. As we will see. and as we have seen. this adaptation is natural with inheritan e. Su h partitioning is helpful in understanding the behaviour of the program and also he king that it is orre t: we an onsider testing the parts separately for example. You will adapt the lasses for your use. Most likely. Next we will dis uss the design of the graphi s in simple pp. In the rest of this hapter we will see two ase studies. It will turn out that this way of writing makes it easier to maintain and extend.ned manner. Inheritan e plays a substantial role in its design. similar proje ts). we will see the omposite lass. First we revisit our formula drawing program. Another modern programming trend is the use of omponents.

ne new graphi al obje ts whi h are made 321 .

1: given a mathemati al formula.1 our spe i.1 Formula drawing revisited Consider the formula drawing problem from Se tion 17. 2011. 20. 322 Abhiram Ranade. In Se tion 17. draw it on the graphi s anvas in a ni e manner. Do not distribute by omposing the simple graphi s obje ts we know so far.

In this se tion we will see how the program an written in using inheritan e. goal was to draw the formula su h that operands in sums. dieren es and produ ts were drawn left to right horizontally. A bene. while the dividend and the divisor were drawn above and below a horizontal bar respe tively.

e. i. to draw b we will . For simpli ity. we ignore the problem of a epting input from the keyboard: wea will assume that the formula to be drawn is given as a part of the program.t of this will be that it will be easy to extend the program to in lude new operators. To illustrate this we will implement the exponentiation operator whi h requires the exponent to be written above and to the right of the base.

rst onstru t it in our program by writing something like: + Node f2('/'. new Node(" ")) ). new Node('+'.setSize() and so on. new Node("a"). new Node("b"). These formulae an further be lassi.1 Basi design The use of inheritan e is natural if the entities we want to represent form a ategory and sub ategories thereof.1. we wish to represent mathemati al formulae. and then we an all f2. 20. In the present ase.

that in the Exer ises of Chapter 17 we pointed out that it helps to onsider unary and ternary formulae { you an think of the lass Formula2 as stri tly ontained in Formula. we will have a lass orresponding to general ategory. from whi h the lasses for the sub ategories will be inherited. Naturally. So we have the general ategory of mathemati al formulae. the last operation to be performed is addition. and hen e we will designate it to be in the lass Div.1. and . This will be analogous to the lass Node of Se tion 17. the last operation to be performed is division. Remember.ed based on the top level operators: for example in the formula b a . Prod and Div respe tively representing formulae in whi h the top level operators are +. . Diff. This lass will have a sub lass Formula2 whi h will represent all mathemati al formulae in whi h the top level operator is binary. The algorithm for drawing the formula will be the same. based on the last operation performed to evaluate the formula. This lass will have sub lasses Sum. In the formula a + b . Diff (dieren e). -. and Div. so we will designate it to be of type Sum.2. hen e we will have methods setSize and draw in all lasses. and sub ategories Sum. We will use the lass Formula to represent all mathemati al formulae. Prod (produ t). These will be de.

Here is the de.ned dierently depending upon the type of the operator.

+ .nition of the lass Formula.

virtual void draw(float lx. so we have de lared some of its methods to be pure virtual.} }. we used stru tures instead of lasses. Also note that in Se tion 17. float ly)=0. Do not distribute 323 lass Formula{ prote ted: double width. Now we are more areful about making members visible and hen e we have de. des ent.2. Thus everything was publi . double getWidth(){return width. We do not expe t Formula to be instantiated.1. Abhiram Ranade.} double getHeight(){return height. publi : virtual void setSize()=0.} double getDes ent(){return des ent. 2011. height.

We next de.ned a essor fun tions for width. height and des ent.

Formula* rhs.ne the lass of formulae with 2 operands at the top level. The fun tion will be de. we are using a fun tion op whi h will return it. virtual string op()=0. Instead of storing the operator expli itly. }. lass Formula2 : publi Formula{ prote ted: Formula* lhs.

Next we de.ned only in lasses in whi h the operator is known.

des ent = max(lhs->getDes ent(). lass Formula2h : publi Formula2{ publi : void setSize(){ lhs->setSize(). rhs->getDes ent()).imprint(). rhs->getHeight() .rhs->getDes ent()).1. } }. rhs->draw( lx+lhs->getWidth()+textWidth(op()).ne the sub lass Formula2h of expressions whi h require a horizontal layout. } void draw(float lx. width = lhs->getWidth() + textWidth(op()) + rhs->getWidth(). op()). ly. The only dieren e is that we are using a essor fun tions instead . ly). These fun tion implementations are similar to the ase '+' of the orresponding fun tions on Node(Se tion 17. float ly){ lhs->draw( lx. Text( lx+lhs->getWidth()+textWidth(op())/2.lhs->getDes ent(). rhs->setSize(). ly). height = des ent + max(lhs->getHeight() .4).

rhs = rhs1. } string op(){ return "+". Abhiram Ranade. Noti e that the layout aspe ts have been dealt with in the lass Formula2h. rhs = rhs1.} }. dieren es. width. We an now reate lasses to represent sums.} }. } string op(){ return "*". } string op(){ return "-". We ould analogously de. lass Diff : publi Formula2h{ publi : Diff(Formula* lhs1. Do not distribute 324 of the members height. These lasses merely give a onstru tor. des ent and op is not a data member but a fun tion member. Formula* rhs1){ lhs = lhs1. Formula* rhs1){ lhs = lhs1. 2011. rhs = rhs1. lass Sum : publi Formula2h{ publi : Sum(Formula* lhs1. and the operator.} }. Formula* rhs1){ lhs = lhs1. lass Prod : publi Formula2h{ publi : Prod(Formula* lhs1. and produ ts.

whi h does verti al layout of its operands.ne an Formula2v lass. it is unlikely there will be many operators requiring a verti al layout with a separating horizontal bar. So we dire tly de. However.

Formula* rhs1){ lhs = lhs1. height = lhs->getHeight() + Bheight + rhs->getHeight(). width = max(lhs->getWidth(). des ent = rhs->getHeight() + Bheight/2. } }. ly+ Bheight/2+rhs->getHeight()-rhs->getDes ent()). } string op(){return "/". rhs->getWidth()). rhs->draw( lx+width/2-rhs->getWidth()/2. rhs->setSize(). ly-Bheight/2-lhs->getDes ent()).imprint(). rhs = rhs1. ly). float ly){ Line( lx. lx+width. } void setSize(){ lhs->setSize(). publi : Div(Formula* lhs1. .ne the Div lass. //spa e for horizontal bar.} void draw(float lx. lhs->draw( lx+width/2-lhs->getWidth()/2. lass Div : publi Formula2{ stati onst float Bheight = 20. ly.

2011.4). It also de.1. Do not distribute 325 This orresponds to the ode for the ase '/' in the orresponding fun tions on Node (Se tion 17. Abhiram Ranade.

i.imprint().nes a onstru tor and the fun tion op.e. This orresponds to the ode for the ase 'P' in the orresponding fun tions on Node (Se tion 17. height = textHeight(). We an now give a simple main program whi h an use the above de. lass Literal : publi Formula{ string value. des ent = height/2.1. } }. publi : Literal(string v){value=v. } void draw(float lx. we need a lass to represent literals. float ly){ Text( lx+width/2.value).4). numbers or variables given in the formula. ly. Finally.} void setSize(){ width = textWidth(value).

nitions to render the formula 1 + . e. } getCli k(). 2 451 +35 5 int main(){ initCanvas("Formula drawing"). new Sum(new Div(new Literal("451").getDes ent()).setSize().2 Comparison of the two approa hes At .new Literal("5")). new Literal("35")))). Sum e(new Literal("1").200+e.1. e.getHeight()-e.draw(200. 20. new Div(new Literal("2").

the lass Formula2 only models the fa t that formulae an have two operands. The ode of Se tion 17. In ontrast.1. The lass Formula2h shows how to layout formulae requiring horizontal layout. dierent on erns are separated into dierent lasses. This is true. We an pla e .rst glan e. For example. but the verbosity has bought us many things. nothing more. A key improvement is that we have partitioned the program into manageable pie es. All the omplexity was pla ed into that lass. in the new ode.1 had just one lass. it might seem that the inheritan e based approa h is more verbose than the approa h of Se tion 17.

2011. Do not distribute 326 ea h lass into its header and implementation . Abhiram Ranade.

les. and the main program into a separate .

This way. if we wish.g. horizontal layout) we know that we will likely modify only one small . if we wish to hange something regarding a ertain issue (e.le.

This is a big bene.le.

t of the new approa h. Another important bene.

Suppose we want to implement layouts of exponential expressions. As you will see. we an do this without tou hing any of our old .t arises when we onsider adding new fun tionality to the program.

les (ex ept the main program .

le. of ourse). The key bene. if we wish to use exponential expressions.

The basi idea is to layout the exponent above and to the right of the base.(lhs->getHeight() . } string op(){return "^". ly). float ly){ lhs->draw( lx.lhs->getDes ent()) .3 Adding exponential expressions We will add a lass Pow that will represent exponential expressions. } void setSize(){ lhs->setSize(). The detailed expressions whi h de ide how to position what are obtained in the manner of Se tion 17. then it is very onvenient if one programmer's ode is not tou hed by another. } }. Formula* rhs1){ lhs = lhs1. rhs->draw( lx+lhs->getWidth(). lass Pow : publi Formula2{ publi : Pow(Formula* lhs1.1. ly .rhs->getDes ent() ). rhs = rhs1. width = lhs->getWidth() + rhs->getWidth().4. height = lhs->getHeight() + rhs->getHeight(). Programmers (deservedly) tend to be paranoid about their ode.t of this strategy is: we an be sure that when we add exponential expressions. and the new one by another.1. This will be a sub lass of Formula2 sin e it has 2 operands. des ent = lhs->getDes ent(). there isnt even a remote han e of damaging the old working ode.} void draw(float lx. and this kind of reassuran e is useful. Noti e that if the old ode was written by one programmer. This way there is larity about who was responsible for what. 20. rhs->setSize(). and are left for you to .

new Pow(new Literal("Y"). new Literal("Z"))). The key point to appre iate is that this new ode an be developed independently.gure out. in a new . Using this lass is simple. to represent X + Y Z we simply write Sum(new Literal("X").

only the lass header . without even having the rest of the ode.le.

les would be needed. we would need to have and modify the old ode.1.. . If we had used the oding approa h of Se tion 17.

Do not distribute 20. Although this system is quite small by standards of real graphi s systems. the ore spe i. but only some relevant portions of it. we will not dis uss the entire system here.2 The simple pp graphi s system 327 We will dis uss the role played by inheritan e in the design of the simple pp graphi s system. Brie y stated. Abhiram Ranade. 2011.

2. Let us take item 2 . s ale. e. We will not dis uss issues su h as the pens asso iated with ea h obje t. polygons. or graphi al input. as in the getCli k ommand. rotate. of ourse.g. su h a system must have the following apabilities: 1. move obje t x. whi h means the other obje ts remain un hanged? As you know. manipulate simply means move. It should be able to display the obje ts on the s reen. we have opted for the latter. So in the rest of this se tion. There are also other questions: what kind of primitives is the user to be given? Will the user need to spe ify how ea h obje t appears in ea h frame (like the pi ture frames in a movie) or will the user only state the in remental hanges. move an obje t. And then of ourse there is the question of what kinds of obje ts we an have. This statement is very vague. It must be able to keep tra k of the obje ts reated by the user so far. 3. simple pp supports the following kinds of graphi al obje ts: ir les. It should be able to manipulate the obje ts as requested. turtles and text.g. re tangles. in simple pp. e. in the manner des ribed above. As you know. What does it mean to manipulate obje ts? As you know. ation of the system is: allow the user to reate and manipulate graphi al obje ts on the s reen. we onsider the problem of reating and manipulating the obje ts given above. lines. Clearly.

ir les (. whi h provides fun tions that an draw lines. polygons.rst. simple pp is built on top of the X Windows system. ar s.

lled and non-.

Item 3 is also relatively easy.lled) on the s reen. With ea h obje t we asso iated some on. at the required pla e. So we all these fun tions.

1. in honour of the S rat h programming environment (s rat h. as shown in Figure 20. Inheritan e is useful for fa ilitating many of the a tions des ribed here. The lass asso iated with the ategory of all obje ts is alled Sprite. in what orientation.g. whi h says how large it is to be drawn. ir les. e. To omplete this very high level des ription we need to answer one more question: when should the obje ts be displayed? The simplest answer to this is: whenever the user hanges the state of any obje t.edu). In the Sprite lass we keep all attributes that are ommon to all graphi s obje ts. and then sub ategories orresponding to dierent types of obje ts. and where. these orrespond to sub lasses of the lass representing the ategory ALL of all obje ts. and so do the asso iated lasses. At .mit. lear the entire display and display all obje ts again. Item 1 is also not diÆ ult in prin iple: we merely keep a list or a set of some kind in whi h we pla e ea h obje t. It should be lear that we have the ategory of all graphi al obje ts. Note that this data is distin t from the shape data. So learly.guration data. Our ategories indeed form a heirar hy. where the name is used for a similar on ept. The heirar hy fa ilitates storing of information as follows.

polygons and so on. when a graphi s obje t is to be displayed on the s reen. lines. you might think that pre ious little might be ommon to all the very dierent looking obje ts: ir les. orientation. it will have a position. It will also have . s ale in addition to its shape.rst glan e. But as mentioned earlier.

Polygon et . a tion (a) an be performed independent of the shape of the obje t. a tion (b) is implemented by a paint method in ea h shape lass. Line. Thus in our implementation. In addition. (b) redrawing the obje t on the s reen. we must also onsider fun tion members. As dis ussed earlier these oordinates are given in a spe ially reated oordinate frame. The a tual implementations dierent. while drawing they will be drawn relative to the position of the polygon (as re orded in the Sprite part of its obje t). For example. 328 Abhiram Ranade.2 shows possible ways ontents of the Cir le and Sprite lasses. Figure 20. The lasses Cir le. and you an see them in the ode supplied. This requires two a tions: (a) re ording that the obje t has indeed been moved. 2011. All obje ts will have these attributes. whereas (b) requires the shape information. will ontain the shape related attributes (in addition to all the attributes inherited from Sprite). Suppose we wish to move an obje t. So these attributes be ome data members in the Sprite lass. Cir le ontains a data member alled radius whi h holds the radius of the ir le being drawn. The Polygon lass ontains an array whi h holds the oordinates of the verti es of the polygon.1: Heirar hy of graphi s obje t ategories attributes su h as olour. The move member fun tion is de. and updating its position a ordingly. Clearly. Do not distribute ALL (Sprite) Circle Line Polygon Rectangle Text Turtle Figure 20.

} The paint method is virtual. i < A tiveSprites. then its de laration would be ve tor<Sprite*> A tiveSprites. In summary. for(int i=0.size(). It performs a tion (a) using the attributes available in the Sprite lass. This is similar to the way we used a ve tor of Verb* to store regular and irregular obje ts and invoked the past tense virtual fun tion on them in Se tion 19. Essentially simple pp maintains a ve tor that holds pointers to all obje ts a tive at the urrent instant. The redrawing works as follows. inheritan e gives us three main bene.ned in the Sprite lass. and so the paint method in the lass of the obje t is used.4. Suppose the ve tor is named A tiveSprites. we simply iterate over the queue and exe ute the paint method of the obje t. When the obje ts are to be drawn. Be ause the elements of A tiveSprites have type Sprite*. It then signals that all obje ts need to be redrawn. i++){ A tiveSprites[i℄->paint(). they an hold pointers to any graphi al obje t.

It is easy to organize our data strorage manner: the Sprite lass stores the on.ts.

guration related data and the other lasses .

bool fill. .. publi : Sprite(). double y. 2011. double y.. Sprite(double x. } lass Cir le : publi Sprite{ private: double radius..y.. Abhiram Ranade.2: Possible de. virtual void paint()=0. publi : Cir le(). // s aling fa tor Color fill_ olor. // position on the anvas double orientation. double y). Figure 20.. // Color is a data type in the X windows Xlib pa kage. void init(double x. double radius=10). Cir le(double x... void forward(double dist). double radius=10). // angle in radians made with the x axis double s ale. virtual void paint() }. . . // whether to fill or not .. Do not distribute 329 lass Sprite{ prote ted: double x.

nitions of Sprite and Cir le .

we an add new shapes easily: we simply de. 2011. and iterate over the ve tor. Do not distribute 330 store the shape related data. Abhiram Ranade. we an store pointers to dierent types of graphi al obje ts (but only subtypes of Sprite) in a single ve tor. Finally. Also be ause of polymorphism and virtual fun tions.

without having to modify any existing ode. We have somewhat simpli.ne a new shape lass whi h is a sub lass of Sprite.

We see an example of this sophisti ation next.3 Composite graphi s obje ts We dis uss how you an de.ed the des ription of simple pp graphi s in order to explain the use of inheritan e. 20. The a tual system is more sophisti ated.

ne a lass whose instan es are omposite. On e built.e. you an use the lass in your program to reate instan es. In de. i. a single instan e an ontain several simple obje ts.

The lass Composite whi h we dis uss next.ning a omposite obje t you need inheritan e as we will see. or a single ir le. It will require several simple obje ts that simple pp provides. and often be manipulated together. It would be ni e if you ould design a lass Car whi h you ould then instantiate to make many ars. These simple obje ts will have to be grouped together. we really mean to move all its onstituent parts. will allow you to group together obje ts. We an then de. A ar is a omplex obje t: it annot be drawn ni ely using just a single polygon. Suppose you want to draw many ars on the s reen. if we want the ar to move.g. e.

Our Composite lass primarily serves as a " ontainer" to hold other graphi s obje ts.ne a Car lass by inheriting from the Composite lass. relative to whi h the ontained obje ts are spe i. It has a frame of referen e.

The Composite lass has been de.ed.

forward. You might want the wheels to rotate in addition to moving forward. rotate from the Sprite lass.ned as a sub lass of the Sprite lass. by default everything will go forward. you an override these methods if you wish. Thus it inherits member fun tions su h as move. For example. i. When you all forward on this.e. However. This an be a omplished by overridding. everything inside gets moved. when you move a Composite. suppose your omposite obje t onsists of the body of a ar and its wheels. The Composite lass is designed so that the member fun tions will ause the ontained obje ts to respond appropriately. You an also additionally de.

Using the Composite lass is fairly easy. 20. the ar might have a light on the top and there ould be a member fun tion whi h auses the light to hange olour from white to yellow (suggesting it is swit hed on).1 Ownership A detail we have hidden from you so far is: every graphi s obje t has an \owner". and the Composite lass onstru tor. When we say that obje t X owns obje t Y. There are only three important ideas to be understood: the notion of ownership.ne your own new member fun tions whi h do new things. we merely mean that obje t Y is spe i. For example. This ould be done using a new member fun tion.3.

For the obje ts you have been reating so far. When an obje t is reated as a part of a omposite obje t. the owner was the anvas: the obje ts were drawn in the oordinate frame of the anvas.ed relative to the oordinate frame of obje t X. it must be drawn relative to the frame of the .

and hen e must be owned by the omposite obje t. Do not distribute 331 omposite obje t. Abhiram Ranade. 2011. Thus an important step in de.

Thus so far we did not tell you about this argument. If you want to indi ate a dierent owner. we must pass a pointer to the omposite obje t itself. you instead pass a pointer to that owner. and hen e simple pp made the anvas the owner of all the obje ts you reated. This argument takes value NULL by default whi h simple pp interprets to mean the anvas.ning a omposite obje t is to de lare it to be the owner of the ontained obje ts. To do this. As you know. and you didnt not spe ify the value. the onstru tor of every graphi al obje t is provided with an optional argument named owner. inside the de. Sin e we reate ontained obje ts in the body of the omposite.

the keyword this denotes a pointer to the obje t. double y.nition of an obje t. Composite(double x.2 The Composite lass onstru tor The Composite lass onstru tor has the following signature. 20. Composite* owner=NULL) Here the last argument owner gives the owner of the omposite obje t being de. So the extra argument must have this as its value.3.

The owner argument must be spe i.y give the oordinates of the omposite obje t in the frame of its owner. it is taken as NULL. and x. As mentioned earlier. if you do not spe ify this argument. indi ating that the anvas is the owner.ned.

g. So we will model a ar as a omposite obje t. Our ar will onsist of a polygonal body. 20.3. wheels).g. body) or other omposite obje ts (e. and lines representing the spokes. So the wheel will itself have to be represented as a omposite obje t. But note that a wheel itself ontains a ir le representing the rim.ed if this omposite obje t is itself a part of another omposite obje t.g. Note that we allow one omposite obje t (e. and two wheels. onsisting of the body and the wheels. a ar) to ontain other ordinary obje ts (e. We begin by de.3 A Car lass We now onstru t a Car lass. This kind of ontainment is allowed and we will see an example shortly. We will give the wheels some personality by adding in spokes.

50. . double y. publi : Wheel(double x.y. 0. this).ning a lass for wheels.this). for(int i=0. i<10. Composite* owner=NULL) : Composite(x.0. Line *spoke[10℄. } } }. i++){ spoke[i℄ = new Line(0. 50*sin(i*PI/5).owner) { rim = new Cir le(0. lass Wheel : publi Composite{ Cir le *rim. 50* os(i*PI/5).

Abhiram Ranade. 2011. Do not distribute 332 There are two private data members. The member rim whi h is de.

This is a very ommon idiom for de. Likewise spoke is an array of pointers to ea h spoke of the wheel.ned as a pointer to the Cir le obje t whi h represents the rim of the wheel. The obje ts themselves are reated in the onstru tor.

as dis ussed earlier. The initialization list Composite(x.ning omposite graphi s obje ts.owner) merely forwards these arguments so that the ore omposite obje t is reated at the required oordinate and gets the spe i. The onstru tor ustomarily takes as argument a pointer to the owner of the omposite obje t itself. and the position of the omposite obje t in the frame of the owner.y. It is ustomary to assign a default value NULL for the owner parameter.

0. Wheel* w1.-200}. the body is reated as a polygon. // super lass forward fun tion w1->rotate(dx/50. {-150. w1 = new Wheel(-90.-100}. lass Car : publi Composite{ Polygon* body.this). } }. {-75. body = new Polygon(0. We have provided a parameter in the onstru tor whi h an be used to give a olour to the body. } void forward(double dx.ed owner. publi : Car(double x.0}.false). 9. the last argument is set to this. this). So we reate the ir le representing the rim.0. and as you an see we have given it an extra argument this. Color . as we want them to be. The Car lass an be put together by using Wheel instan es as parts. Inside the onstru tor.this). {50.0. Finally. // angle = dx/radius w2->rotate(dx/50.false).-100}. {-150.false). w2 = new Wheel(90. body->setFill(). bodyV. and even here the extra argument this auses the lines to be owned by the Wheel obje t. Likewise we reate lines at dierent in linations to represent the spokes.y.-100}. Wheel* w2.owner){ double bodyV[9℄[2℄={{-150. As will be seen. For all 3 parts.0}. The de. {-100. we reate the sub-obje ts. the wheels are reated. Composite* owner=NULL) : Composite(x. double y. bool repaintP=true){ Composite::forward(dx. so that the Wheel obje t be omes the owner of the rim. body->setColor( ). In the onstru tor. be ause of whi h the parts be ome owned by the Car obje t.0}}.-200}. {150. {150.-100}. if(repaintP) repaint(). {100. the private members are the pointers to the body and the two wheels.

As dis ussed. whi h is a omplished by alling the forward fun tion of the super- .nition also shows the forward fun tion being overridden. we want the ar to move forward.

But we also want the wheels to turn. then the wheels must rotate by dx/r radians. Abhiram Ranade. Clearly. if the ar moves forward by an amount dx. But why does the rotate fun tion alled with an extra argument false? And why is the fun tion repaint alled? We explain these next.4 Frames Another detail of simple pp graphi s whi h we have withheld from you is that all the on. this is a omplished by rotating them.3. Do not distribute 333 lass. 20. 2011. where r is the radius of the wheels.

If repaintP is true. rotate and so on have an additional argument repaintP whi h takes the default value true. move.2 after every on. then the anvas is repainted as dis ussed in Se tion 20.e.guration hange ommands. i. forward.

then the repainting is not done. If repaintP is false. only the on.guration hange.

This feature is useful espe ially when invoking a on.guration hange is re orded.

We do not want repainting to happen after a move of ea h subobje t. Rather we want repainting to happen on e. after the on. It is ineÆ ient and also auses visually annoying.guration hange ommand on subobje ts omprising a omposite obje t.

20. here is a main program that might use the above de.->rotate operations..3. Repainting is done only at the end unless it is disabled by the aller to Car::forward. This is what the ode above a omplishes: no repainting happens after the Composite::forward as well as the two w.5 Main program Finally..guration hange is re orded for all subobje ts.

Car (300. i<100.false).800.300. d. one blue and another red. we move the ars forward. Further.5.600.COLOR("red")).s ale(0. repaint(). i++){ . The main program reates two ars. The red ar is then s aled to half its size. Car d(300. } getCli k().false). the wheels of the smaller ar should appear to have twi e as many rotations per unit time be ause the smaller wheel has half the radius but is travelling the same distan e as the larger wheel. .800).forward(3.0. Finally. int main(){ initCanvas("Car".0. the ar wheels should appear to roll on the ground. } for(int i=0.nitions.5).0.forward(1. When you exe ute this.COLOR("blue")). This auses all the omponents of the ar to shrink { this is handled automati ally by the ode in the Composite lass. d. getCli k().

1 add the apability of drawing summation formulae. B. C an themselves be formulae. 2011. 334 Abhiram Ranade. formulae B X A C where A. Do not distribute Exer ises 1. i.e. 2. To the program of Se tion 20. De.

De.ne a omposite obje t to model a fa e.

you an reate the ee t of the bird ying. smiling. and another in whi h the wings are spread out. Do you think it will be possible to design a lass CostumedObje t whi h an make it easier to de. An attra tive idea in the S rat h programming system is of ostumes for sprites. e. 4. 3. a bird sprite might have two ostumes: one in whi h the wings are together. By alternating between the two ostumes as the bird moves. A ostume is merely a des ription of how a sprite an appear. For example. Design this sprite.ne methods for showing emotions.g. Use your imagination.

ne multiple ostumes? If so do it. .

say 7pm to 10pm. As a on rete example. servi e might will be slower and ea h ustomer will o upy the table for longer periods. So we might want to determine. i. we onsidered the simulation of heavenly bodies. suppose we want to de ide how many dining tables we should put in a restaurant. say during whi h he eats. predi t the state of the system at some later date. the probability that a ustomer arrives in any given minute of the \busy period" for restaurants. If we put too few tables. and the possibility that a ustomer party might need more than one table. it will be mu h more 335 . In this ase. easily evaluatable fun tion of the dierent parameters. On arrival. as might be required in astronomy. Knowing the revenue and the ost of putting up tables. we should be able to hoose the right value of T . However. what our revenue is likely to be. For simpli ity. and when. A very ommon use of simulation is to understand whether a fa ility su h as a restaurant or a train station or airport has enough resour es su h as tables or platforms or runways to satisfa torily serve the ustomers or travellers that might arrive into it. we implied that the eating time probability distribution e(t) is a fun tion only of t. a ustomer o upies the table for some time. For example. terrestrial systems. the number of tables we have? Note that an arriving ustomer will leave if all tables are o upied. for ea h T where T is the number of tables we put. Suppose that we are also given a fun tion e(t). But this is often not possible if the probability model is omplex. We will assume that we are given p.Chapter 21 Dis rete event simulation We have already dis ussed the general notion of simulation: given the urrent state and laws of evolution of a system. Problems su h as this one an sometimes be solved analyti ally.e. But if there are many people in the restaurant. and then leaves. However. for simpli ity we will assume that ustomers arrive individually and are seated individually at separate tables. we an write the expe ted revenue as a reasonably simple. in the above des ription. This of ourse is predi table only statisti ally. that gives the probability that a ustomer eats for t minutes. we will not be able to a ommodate all ustomers who might want to eat in our restaurant. suppose that the revenue is proportional to the total number of ustomers. we of ourse need to know something about how many ustomers want to eat in our restaurant. On the other hand. To do this analysis. simulation is very mu h used for more mundane. In Chapter 15. ea h table we put in has a ost. we should onsider not single ustomers but a party onsisting of several ustomers. Ideally. Can we determine the total revenue for an arbitrary value of T . Thus perhaps the distribution should be a fun tion of the number of ustomers present as well.

for ea h time step we omputed what happens to ea h star. whi h we will all the oee sha k simulation. In the osmologi al simulation. where a step again might be hosen to be a small enough time interval. By this we mean the following. and then some.1 Dis rete event simulation overview In prin iple. whi h we onsider at length in Se tion 21. We will develop some ma hinery to perform dis rete event simulations using whi h we will perform the restaurant simulation. While this approa h. The total pro essing eort in this program organization is proportional to at least the produ t of the number of entities in the simulation (stars or ustomer parties) and the number of time steps. every simulation an be programmed in the manner of the osmologi al simulation. Similarly we ould ompute what happens to ea h ustomer at ea h step. We will see that it is an example of a Dis rete Event Simulation. In su h ases. Using this information we ompute how many tables are o upied at ea h instant. 2011. a ommon strategy is simulate the system. The last topi in this hapter is the shortest path problem for graphs. say a minute. Do not distribute 336 diÆ ult to write down an analyti al solution.1. whi h uses the ma hinery we develop in this hapter. how long they wait. In Chapter 22 we develop a simulation of an airport. We will also onsider a variation. 21. We an get a fast algorithm for this abstra t problem by viewing it as a simulation of a ertain natural system. Abhiram Ranade. We pi k random numbers from appropriate distributions to de ide when ustomers arrive. often alled the time-driven approa h. In this hapter we will see how to perform this simulation. is . This simulation has a very dierent hara ter from the osmologi al simulation of Chapter 15. whi h ustomers need to be turned away be ause the restaurant is full and so on.

and the . it is likely to be very ineÆ ient for the restaurant simulation. Suppose we have some T tables. We explain the key idea with an example.ne for the osmologi al simulation.

rst T ustomers arrive (say that is how the random numbers got hosen) at time steps 1 through T . Now. Clearly ea h of them will be given a table. for ea h of these T ustomers we have (suitably randomly) .

Then we know that nothing of interest happens in our simulation between step T + 1 to step t: the ustomers who were eating will keep eating. The system to be simulated onsists of a set of a tive elements whi h we will refer to as entities. Suppose among the departure times of these ustomers. or dis rete. and hen e the time at whi h they will depart. o urren e. Hen e this approa h is alled the Dis rete Event Simulation approa h. in whi h we painfully examine ea h entity at ea h step. an entity an examine and . The phrase \important event" is to be interpreted in the sense of an event that an hange the state of some entity. When awake. In the new approa h. a dis rete event simulation works as follows. and some additional passive elements. \what is the earliest important event that will happen next?". and the arrival times of the remaining ustomers. Thus we an dire tly jump to step t and pro ess the departure or arrival whi hever was supposed to happen then. the smallest number is t. Further. If the earliest important event will happen at some time step t and the urrent time step is T . then we an dire tly jump to step t. In general. Entities an be awake or dormant. This will learly be more eÆ ient than the time driven approa h.xed the time for whi h they will eat. we are essentially asking. we use the term event in the sense of an instantaneous. The fo us in this approa h is on the important events in the system.

and they are deemed to happen instantaneously. After performing the required a tions. or the state of the passive elements. These a tions are the events. an entity might de ide to be ome dormant for some spe i. An entity may also ause a new entity to be reated. Do not distribute 337 alter its own state or the state of the other entities. Abhiram Ranade. 2011.

we maintain a variable time whi h is used to hold the time till whi h we have simulated the system. e). Then the variable time will hold the value t. we will merely invoke the wakeup fun tion on it. So we will all this set the Wakeup Requests Set (WRS). We then onsider all entities that need to be woken up at t0. an entity may perform various a tions. When that number of steps are deemed to have elapsed. At the start of the simulation. After . As a part of wakeup. Let t0 be the smallest time value that appears in any request in WRS at this stage of exe ution. We sele t some entity e from these and invoke the wakeup fun tion on it. Suppose we have simulated the system till some time t. and WRS is set to ontain a (t. time is set to 0. Finally. More pre isely. We will maintain a set whi h will hold the entities when they are dormant. and then it an perform more a tions/events.ed number of time steps. our set will hold pairs of the form (t. or is known to enter the system at time t. Now learly. nothing of interest will happen in our system between time t and t0. Hen e we an safely set our variable time to t0. We will have a lass simEntity whose instan es will be the entities in the system. then the entity must be woken up. where e is the dormant entity and t the time at whi h it needs to be woken up. e) pair for ea h entity e whi h we know is either present at the beginning and wants to be woken up at time t. To wakeup an entity. The lass will have a member fun tion wakeup. The basi iteration of the simulation algorithm is as follows. in luding examining and modifying program state.

So the last a tion in the fun tion wakeup will typi ally be to insert a (t00 . If the entity has ompletely . an entity may de ide it needs to be ome dormant again. e) pair into WRS. till some time t00 .nishing the a tions required for the urrent wakeup all.

it simply returns from wakeup without inserting anything into WRS. The simulation terminates when WRS is found to be empty. Here is the de. After this the basi iteration repeats.nished everything that it needs to do and wants to leave the simulation.

As you will see. For example.e. This lass is abstra t. }. the super lass simEntity is useful be ause the ode related to managing entities as they go to sleep and wake up an be written on e. lass simEntity{ publi : virtual void wakeup() = 0. it is not expe ted to be used dire tly to reate instan es. The time entity pairs that we need will be represented using the pair lass in STL (found in the header . you will see that the entities will be air raft and these will be instan es of a plane lass whi h will be a sub lass of simEntity. and this will get used for all sub lasses. but instead. onsidering only obje ts of lass simEntity. i.nition of the lass simEntity. a tual entities are expe ted to be instan es of a sub lass of simEntity. in the restaurant simulation we will have a Customer sub lass to represent ustomers. This is a big advantage of the obje t oriented organization. Or later.

We use the type double to represent time. Instead of putting simEntity into the pair.le <util>). we put a pointer . so we need a pair of double and simEntity.

2011. Thus the lass is obtained by writing pair<double. Abhiram Ranade. Note that we are using pointers to entities and not the entities themselves. Do not distribute 338 to it. The pair lass is onvenient be ause the omparison operators work on it: with the omparison happening lexi ographi ally. Comparisons are de. Thus pair (t. e) < (t0 . e0) if t < t0 or if t = t0 and e < e0 .simEntity*>.

There is nothing spe ial as far as the manner in whi h pairs get inserted into the set. in the sense de. we an merely demand \a smallest pair (t. p) where t is smallest".ned on pointers (they are treated as unsigned integers for this purpose). Thus instead of needing to demand \a pair (t. p)". However. Next we say how to represent the set WRS in whi h we will store these pairs. removal from WRS happens in a very spe ial manner: we always remove only a smallest pair from those stored.

The priority queue template lass in STL (found in header .ned above.

but not quite. Thus if we want to reate an instan e pq of this lass we would write: priority_queue<pair<double.le <queue>) supports exa tly this mode of operation and is thus ideal for implementing WRS.simEntity*> > pq.simEntity*> by writing priority queue<double. For this de. This is almost what we want. We an obtain a lass for prioirty queues of pair<double.simEntity*>.

In this ase. and possible default values. To get a smallest instead. Thus a largest element is returned. It defaults to less. the priority queue template takes 3 arguments. whi h is as follows. lass mp = less<typename C::value_type> > priority_queue. whi h is simply the operator <. Thus a priority queue returns that element x su h that there is no y su h that x < y. template< lass T. we must make the third argument be the > operator.nition. we need to know the prototype for priority queue. A prototype of a template is similar to a fun tion prototype: both give the arguments and their types. To hange the default behaviour. and this is spe i. the method top will return the largest pair in the queue. lass C = ve tor<T>. The third argument mp is used to de ide what to return. But we an hange this behaviour so that it instead returns the smallest.

simEntity*> > in our ase. we must also spe ify a value for the se ond. Thus we de. But to spe ify a non-default value for the third argument.ed as greater<pair<double.

simEntity *pP){ pq.ne the lass as shown.empty()){ pair<double.} void insert(double sleepTime.top(). . lass simQueue { // ************* Implementation version 1 ************* double time. publi : simQueue(){time=0. ve tor<pair<double.simEntity*>.push(make_pair(time+sleepTime. priority_queue<pair<double.simEntity*> >. greater<pair<double.simEntity*> sqe = pq.pP)).simEntity*> > > pq. // wakeup at urrent time + sleepTime } void pro ess_till_empty(){ while(!pq.

2011.pop(). sqe. The . Abhiram Ranade. } WRS an be represented using an instan e of simQueue. return out.first. Do not distribute 339 pq.se ond->wakeup(). } } ostream & log(){ out << time << ") ". }. time =sqe.

greater<pair<double.simEntity*> >. double simQueue::time = 0. It is used to print messages to the s reen. so that is not repeated.simEntity*> > > simQueue::pq. The instan e variable time is updated. it repeatedly pi ks the smallest element in the queue and wakeups the entity. simEntity *pP){ /* as before */ }. is for reporting onvenien e. publi : void insert(double sleepTime. for inserting a wakeup request. lass simQueue { // ** Real Implementation ** stati double time.simEntity*>. The method pro ess till empty does as it says. ve tor<pair<double.simEntity*>. stati void pro ess_till_empty(){ /* as before */ }. The last method. greater<pair<double. ve tor<pair<double. The new implementation is based on the observation that in any simulation we will have only one WRS. priority_queue<pair<double. we implement WRS using stati variables in the lass simQueue as shown. The implementation of the fun tions insert. Note that a referen e to the onsole output. As you will see this is slightly more onvenient.simEntity*> > > pq.simEntity*> >. Note the de. out is returned. The pair is then inserted into the priority queue. We ompose a pair from the wakeup time and the entity pointer using the make pair provided in the pair template lass. stati ostream & log(){ /* as before */ }. or we an just examine it using the top method. as will be seen in the next se tion. Note that the smallest element in the queue an be removed by using the pop method. pro ess till empty and log is as before. So. However.rst method supported by simQueue is insert. }. we will give an alternate implementation whi h we will use in the rest of the hapter. stati priority_queue<pair<double. This is a perfe tly adequate representation. so that the rest of the message an be appended using the << operator. log. but ea h message is prefa ed by the urrent time.

nition of the stati variables simQueue::time and .

Abhiram Ranade. Stati variables only get de lared when they are mentioned in the lass de laration. Do not distribute 340 at the end. 2011. and must be de.

ned outside the lass de laration. For the new implementation. We already have the set WRS represented. To print messages pre. We an insert into it using the fun tion simQueue::insert and to pro ess the inserted pairs we all simQueue::pro ess till empty. as shown. we do not need to instantiate the lass simQueue.

2 The restaurant simulation Suppose for the sake of de.xed by the urrent simulation time we all simQueue::log. simQueue::pq 21.

This is the system we want to simulate. This will be a sub lass of simEntity.niteness that we have a restaurant with 5 tables. We will use the simEntity and simQueue lasses given above. Suppose that the eating time for a ustomer is in the range 21-40 minutes. The main program is given . We will represent ustomers using a Customer lass. in whi h at ea h minute between 7pm and 10pm a ustomer arrives with probability 1/10. with all durations equally likely.

The ustomer obje t if reated is inserted into simQueue. a ustomer is generated with the required probability.rst. for(int t=0. Then for ea h t.1). } }. where t represents ea h of the 180 minutes between 7 and 10 pm. For generating random numbers. &restaurant)). } simQueue::pro ess_till_empty(). to be woken up at time t. the number that is o upied.40 simQueue::insert(t. // number of tables o upied double arrivalP. } Next we present the de. // number of tables in the restaurant int nO upied . double ap) : apa ity( ). we use the fun tion randuv from Se tion 8.0. // restaurant has 5 tables. t<180.1 int ustomer_id = 0. Restaurant(int . It begins by reating a restaurant obje t in whi h we hold the information about the number of tables. // uniform between 21. and the ustomer arrival probability. arrivalP(ap) { nO upied = 0.1. The time that ea h ustomer spends eating is generated to be a random number between 21 and 40. // arrival probability = 0. eatingT. stru t Restaurant{ onst int apa ity. new ustomer(++ ustomer_id.1) <= restaurant.7.arrivalP){ double eatingT = randuv(21. int main(){ Restaurant restaurant(5. t++) if(randuv(0.40).

A ustomer is woken up .nition of the Customer lass. The main part in this is the a tion the ustomer takes when woken up.

rst when time be omes equal .

2011. If so. in our simplisti model. i. During the eating pro ess the state of the ustomer does not hange. Do not distribute 341 to the time at whi h the ustomer is supposed to arrive. When this all to wakeup happens. After the eating time eatingT elapses. and so for the purposes of the simulation the ustomer an be thought of as be oming dormant. Abhiram Ranade. Thus if the ustomer does .e. the ustomer enters and will start eating immediately. the a tions of the ustomer as he arrives at the restaurant must be mimi ked. the time for whi h it is reated in the above ode. On arrival the ustomer an enter the restaurant if there is an uno upied table. the ustomer must leave the restaurant.

nd a table. then the ount of o upied tables is in remented. and the ustomer is inserted ba k into WRS. At this point the eating time is spe i.

the wakeup fun tion is again alled. This time the wakeup fun tion must merely print out a message that the ustomer is leaving the restaurant. there an be two alls to the fun tion wakeup. When this duration elapses. Thus for ea h ustomer. on arrival and after .ed as the duration for whi h the ustomer will be dormant.

To distinguish the two ases. ase 1: // if was eating. // set state to eating. eatingT(t). --pRest->nO upied. whi h ended. double eatingT. Depending on the value of state. // initial state = about to enter } void wakeup(){ swit h (state){ ase 0: // if about to enter if(pRest->nO upied >= pRest-> apa ity){ simQueue::log() << " Number of o upied tables: " << pRest->nO upied << " Customer " << id << " disappointed. We use the value 0 to indi ate that a ustomer is just entering and a 1 to indi ate that a ustomer is eating. ++pRest->nO upied. } return. publi : ustomer(int i. the fun tion wakeup will exe ute appropriate ode. lass Customer : publi simEntity{ int id.nishing eating. . Restaurant pRest.\n". in ea h Customer obje t we will have a data member state. simQueue::insert(eatingT. state = 1. simQueue::log() << " Number of o upied tables: " << pRest->nO upied << " Customer " << id << " finishes. Restaurant *ptr) : id(i). } else{ simQueue::log() << " Number of o upied tables: " << pRest->nO upied << " Customer " << id << " entered. double t. pRest(ptr) { state = 0. int state.\n".\n".this).

Abhiram Ranade. or is already reserved by this simEntity. We will implement a resour e whi h keep tra ks of who (whi h simEntity) is using it. Finally. This returns true if the resour e an be reserved for this simEntity. then the new ustomer must wait. knowing who is using the resour e will make this lass more useful.3. all of whi h require some eort and time from the server. instead. Otherwise. Suppose the sha k serves beverages and food.1 A Resour e lass The key notion is that of a Resour e lass. We also put that entity into simQueue with a delay of 0 so that it will be woken up in the urrent step itself. Release is implemented as follows. we merely mark the owner of the resour e to be NULL. 21. false is returned. 21. So a line of waiting ustomers might form at popular oee sha ks. a resour e an be released.3 Simulating a oee sha k Consider now. publi : Resour e(){owner = NULL. simEntity* owner. 2011. If a resour e annot be reserved. lass Resour e{ queue<simEntity*> q. if a departing ustomer wakes up the next ustomer in the queue so that the next ustomer an be served. } } 342 return. Do not distribute }. It is more eÆ ient. This is the idea we will implement. they wait in a queue. in an instan e variable (owner). One way to deal with this is so alled busy waiting: periodi ally (say every minute) the entity wakes up to he k if the resour e has be ome available. A simEntity an attempt to a quire the resour e by alling the reserve method.}. We ould have merely kept tra k of whether the resour e is in use or not by using a boolean instan e variable. then we make the entity at the head of the queue be the owner. If no entity is waiting. and if it is in use. Given the probability of ustomer arrival and the probability distribution of the servi e time. Customers try to reserve the resour e. If some entity is waiting. If a ustomer arrives while the server is busy with a previous ustomer. an we predi t how mu h business the sha k gets and also how long the line be omes? Now we need to model a simulation entity ( ustomer) waiting for a resour e (server's attention) to be ome available. For this we will use the queue lass in STL.size(). a roadside oee sha k manned by a single server. a simEntity may hoose to await its availability. int size(){ return q. } bool reserve(simEntity* pS){ if (owner == NULL) . This is implemented simply by putting the simEntity on the queue asso iated with the resour e.

Sna ker(int i. new Sna ker(++ id. } simQueue::pro ess_till_empty(). }. q. We reate a Resour e to model the server. } 21.2 The simulation Using the Resour e lass. simQueue::insert(t. } void release(){ if(!q. // should be alled only if reserve fails. t<60. Resour e &s) : id(i).owner). The general outline is as before.1) <= arrivalP){ double servi eT = randuv(minServi eT. the simulation is easily written. int t. int main(){ onst float arrivalP = 0. } void await(simEntity* pS){ q. server)). minServi eT=3. t++) // 60 minute duration if(randuv(0. int id = 0. whi h is alled server in the ode. return owner == pS. Resour e server. 2011. maxServi eT=9. maxServi eT).front(). server(s){ . Then for ea h minute we generate a ustomer. int state. servi eT(t). simQueue::insert(0. Do not distribute 343 owner = pS.empty()){ owner = q. Abhiram Ranade. The ustomer in this ase is an instan e of the lass Sna ker whi h we des ribe below. int servi eT. servi eT. } for(int t=0. with the arrival probability arrivalP.push(pS).15. lass Sna ker : publi simEntity{ publi : int id. Resour e &server. } else owner = NULL.3. The main program for simulating a 60 minute duration is as follows.pop().

break. } } We . ase 2 : simQueue::log() << " Customer: " << id << " finishes.this). if(!server. 344 Abhiram Ranade.this). simQueue::log() << " Customer " << id << " in queue. state = 0. } void wakeup(){ swit h (state){ ase 0 : ++state.\n". else simQueue::insert(0. ase 1 : ++state. server.\n". simQueue::log() << " Customer " << id << " being served.release(). Do not distribute }. simQueue::insert(servi eT.\n".await(this). 2011. break.reserve(this)) server.

2). Note that the argument s to the onstru tor is a referen e to the server. the member server is also a referen e variable (Se tion 11. and use it during the lifetime of Sna ker. Thus we an save the referen e in the referen e variable. The Sna ker will potentially be woken up thri e: .rst remark about the onstru tor for Sna ker.2. and not a pointer to the server. The behaviour of the Sna ker is more omplex than that of the Customer. Similarly.

rst on arrival. and . se ond on getting a ess to the server.

nally when the servi e .

So we need a state variable whi h will take values 0. state 2 This is the ase in whi h the servi e has .2. then the ode in Resour e will ause the sna ker to be put into simQueue for the next step. If the server an be reserved.nishes. Based on this variable. For this. If the server annot be reserved. servi eT. The sna ker tries to reserve the server. The a tion in this ase is simple. For this the sna ker puts itself ba k into simQueue to be woken up after its servi e time. the sna ker puts itself ba k into simQueue with sleep time of 0. then the sna ker is ready to start being served.1. we must model the sna ker being served. whi h happens in the next state. When the resour e be omes available. then the ustomer must wait for the resour e. appropriate ode will be exe uted. state 0 This is the ase representing arrival of the sna ker into the oee sha k. state 1 This is the ase when the sna ker has got a ess to the server.

We are using referen e variables just to show how referen e variables an be used. 1 .nished. 1 Analogous to what we did in the restaurant simulation. we ould have only used pointers.e. nothing is put on simQueue. So the sna ker just leaves. i.

2011. Do not distribute 21. Abhiram Ranade. so alled be ause we wanted to .6 was the all-sour e-shortest-path problem.4 Single sour e shortest path 345 The shortest path problem we onsidered in Se tion 13.

6. In this se tion we onsider the single-sour e-shortest-path problem. i.nd the lengths of the shortest paths from all ities to all other ities. we want to know the distan es from just one of the ities.e. to all other ities. we will fo us on the problem of . We will use the term distan e to denote the length of the shortest paths. As in Se tion 13.

the paths themselves an be identi.nding the distan es.

is mu h faster than the algorithm of Se tion 13. whi h is left for the Exer ises. Dijkstra's algorithm an be viewed as a omputer analogue of the following physi al experiment you ould undertake to . The algorithm we dis uss here. attributed to Edsgar Dijkstra.6. whi h will be referred to as the sour e.ed with a little additional book-keeping. in what follows. So learly this algorithm is more suitable if you want the distan es from just one ity.

say 1 km/minute. Spe i.nd the distan es. For the experiment we need many y lists who an ride at some onstant speed.

here is how they ould . If we do have su h y lists. we need to have as many y lists in ea h ity as there are roads leading out of it. ally.

and we want the distan es from Nashik. Here is what happens when a y list rea hes her destination. and the job of the y list will be to travel on that road when asked. all the y lists assemble in their respe tive ities. the y lists in the sour e ity start pedalling. we have a y list waiting. Mumbai and Pune. for ea h road in our map. suppose our graph is the map of Figure 13. So at time 0. Thus at the beginning. As an example. three y lists start pedalling from Nashik to respe tively Nagpur. To start with. At time 0 the y lists in the other ities do nothing.1. Ea h y list is assigned one road leading out of the ity. At some time whi h we will all 0. If she is the .nd the length of the shortest paths.

then she signals the y lists waiting in the ity to start pedalling.rst person to rea h that ity. If she is not the .

Continuing our example. the y list from Nashik would arrive at time 200 into Mumbai. where we are measuring time in minutes from the start.e. someone arrived earlier. she does nothing. i. She would be the .rst y list to arrive into the ity.

However. when she rea hes Pune. Of these 3 the y list heading to Pune would rea h 160 minutes later.rst one to arrive there. she would have found that the y list from Nashik has already arrived at time 220. so she would ag o the 3 Mumbai y lists who would then start travelling towards Kolhapur. So the y list arriving from Mumbai into Pune would need to do nothing. Pune. at time 360. The experiment ends when all the y lists have . and Nashik respe tively.

We will show that: (a) the length of the shortest path from the sour e to any ity is simply the time in minutes when the earliest y list arrives in that ity! (b) we an use dis rete event simulation to simulate this system.nished their journey. We explain (a) .

and C be any ity. Let S denote the sour e ity.rst. Let t be the time at whi h the .

There. Eventually.rst y list arrives into C . note that we are not only going ba k in time but also ontinuously travelling ba k. Thus. ba kwards. We argue that there must be a path from S to C of pre isely this length. In this pro ess. at time 0. we must rea h the ity S . To see this. onsider the y list that arrives into C . we must have overed. We follow this y list ba kward in time to the ity from whi h he started. he was agged o by some other y list. whom we follow ba k in time. at 1 km/minute. and so on. .

346 Abhiram Ranade. Thus we have proved that there exists a path from S to C of length equal to the time at whi h the . Do not distribute exa tly the same distan e as the time taken. 2011.

and k = C . Let di be the distan e from to i along the path. We now prove that it is the shortest. . Consider a shortest path P from S to C . the ities on it being . We will prove that the . k in order. with = S .rst y list arrives in C . : : : .

Hen e it follows that the . Hen e he will arrive at i at time at most di + di di = di . for all i. But we proved that the time of arrival must equal the length of some path. Thus we know that some y list must arrive at k = C at time at most the length of a shortest path P . Thus the indu tion is omplete. But this y list travels at 1 km/minute. Clearly.rst y list leaves i latest at time di. this is true for i = 0: indeed a y list leaves at 0 = d . So assume by indu tion that a y list leaves i at di or before. and requires di di time to travel from i to i .

0 0 1 0 0 0 +1 +1 +1 21.1 Dijkstra's algorithm as a simulation +1 +1 The .4. We next show that our algorithm an be programmed as a dis rete event simulation.rst y list arrives at time exa tly equal to the length of the shortest path.

Ea h vertex obje t ontains a ve tor edges whi h stores information about the edges leaving that vertex.rst question. of ourse is how to represent the graph. We use a dierent representation. Suppose G is a Graph. Then G.edges[j℄ stores information about the jth edge leaving vertex i.1 similar to the representation for trees dis ussed earlier. verti es. the ith element of whi h is an obje t of lass vertex ontaining information about the ith vertex. shown in Figure 21. spe i.6.verti es[i℄. The main lass is Graph whi h holds a ve tor. We ould use the same representation as in Se tion 13.

The member arrivalT in ea h vertex obje t is meant for storing the time at whi h the . (b) a double length giving the length of this edge. ally it holds the following: (a) a pointer vptr to the vertex whi h is the other endpoint of this edge.

Note that length and arrivalT are needed spe i.rst y list arrives into that vertex.

The lass Graph ontains a onstru tor whi h an read in the graph from the . then you would not have these members but possibly some other members. ally for our simulation. if you want to develop other graph algorithms.

2 shows a sample input .le whose name is given as an argument. Figure 21.

le. This .

1.le represents the graph of Figure 13. The .

rst number in the .

whi h represents 1. This will ause elements of the ve tor verti es to be reated.le gives the number of verti es. The onstru tor sets the size of the array verti es to this number. Thus a vertex obje t is reated for ea h vertex in the graph. Note the onstru tor for vertex: it sets arrivalT to HUGE VAL. This serves to denote that as of now. the member arrivalT is unde.

where v1. as well as in verti es[v2℄ whi h stores information related to vertex v2. the onstru tor reads information about edges in the graph. v2. When the loop . This onsists of triples v1. Next.ned. We must store the information about this edge in the stru ture verti es[v1℄ whi h stores information related to vertex v1. and dist gives the distan e between the endpoints. That is done in the two statements in the loop. dist. v2 give the endpoints of the edges.

Thus we must de. We will dis uss the wakeup member fun tion later. the graph will have been onstru ted. Note that the stru ture vertex ontains a ve tor of edge obje ts.nishes.

ne .

1: Graph representation 347 . Figure 21. verti es[end2℄. infile >> n.push_ba k(edge(&verti es[end1℄.length. 2011.push_ba k(edge(&verti es[end2℄. int n. not definition. stru t Graph{ ve tor<vertex> verti es. while(infile >> end1){ infile >> end2 >> dist. double d){vptr = vp.edges.edges. i++){ simQueue::insert(edges[i℄. } } }. double dist. end2. length = d. double arrivalT. verti es[end1℄.} }. int end1. Graph( har* infilename) { ifstream infile(infilename). for(int i=0. stru t edge{ vertex* vptr. i<edges. edges[i℄. // forward de laration. stru t vertex : publi simEntity{ ve tor<edge> edges. double length. } } } }.vptr).resize(n).} void wakeup(){ if(arrivalT > simQueue::getTime()){ arrivalT = simQueue::getTime().dist)).dist)).size(). edge(vertex* vp. verti es. vertex(){arrivalT = HUGE_VAL. Do not distribute stru t vertex. Abhiram Ranade.

Do not distribute 348 File ontent Explanation 6 Number of ities 0 1 450 Kolhapur Mumbai distan e 0 5 350 Kolhapur Satara distan e 1 2 160 Mumbai Pune distan e 1 3 200 Mumbai Nashik distan e 2 3 220 Pune Nashik distan e 3 4 500 Nashik Nagpur distan e 5 2 50 Satara Pune distan e Figure 21.2: Input . 2011. Abhiram Ranade.

le for graph of Figure 13.1 the lass edge before de.

the stru ture edge ontains a pointer to a vertex obje t. However. This might seem to require that we de.ning the lass vertex.

This is not true.ne vertex before edge. it suÆ es if vertex is de lared before edge. This is done by the . sin e edge only ontains a pointer to vertex.

har** argv){ Graph G(argv[1℄).arrivalT << " ". int main(int arg . The program uses ommand line arguments.verti es.verti es[i℄. The .rst line of Figure 21.wakeup(). } // Flag off the y lists in sour e // Simulate until all y lists finish. i<G. as we explain below.size(). for(int i=0. out << endl. stringstream(argv[2℄) >> sour e.verti es[sour e℄. simQueue::pro ess_till_empty(). // index of sour e ity G. The main program reates the graph. // argv[1℄ = name of file from whi h to read graph int sour e. i++) // print all arrival times out << G.1. and starts of the simulation of the movement of the y lists.

rst ommand line argument argv[1℄ gives the name of the .

le whi h ontains data to build the graph. We supply this .

For this we . argv[2℄ is expe ted to be an integer.le name to a onstru tor of the lass Graph whi h builds a graph obje t G for us. The se ond ommand line argument. and it gives the index of the sour e node.

Then we start o the simulation. When a y list arrives. For this we need to in lude the header <stringstream>. wakeup does whatever is supposed to happen when a y list arrives.rst onvert the string argv[2℄ to a stringstream. The arrival of a y list into ity i orresponds to exe ution of G. and then read from it.wakeup(). These are the only events in our simulation. the arriving y list must he k if she is the . The important event in the simulation is the arrival of a y list into a ity.verti es[i℄.

and is hanged only during the exe ution of .rst to arrive. Note that arrivalT was set to HUGE VAL when the vertex was reated.1 does the following. It he ks whether the member arrivalT is HUGE VAL. the fun tion wakeup as implemented in the lass vertex in Figure 21. Correspondingly.

Abhiram Ranade. then this y list is the . Thus if arrivalT still equals HUGE VAL. 2011. Do not distribute 349 wakeup.

pointed to by edges[i℄.length. Hen e.vptr) after edges[i℄. The y lists must be agged o to leave the urrent vertex. A y list must be agged of for ea h neighbouring ity i. after overing the distan e edges[i℄. 2. then it must have been set to a .e. Re ord the orre t arrival time into arrivalT. If arrivalT is not HUGE VAL. and it must do the following: 1. Hen e we insert a request in simQueue to wakeup *(edges[i℄. i. after that mu h time.length minutes from the urrent time.vptr. The y list will rea h the orresponding ity.rst to arrive.

After that. main merely waits for the simulation queue to be empty. To start o the simulation.e. In that ase the urrent y list must do nothing. and hen e this is what is alled by main. i. for all y lists to .e.nite value in some previous wakeup all. we must ag o the y lists in the sour e vertex. The member fun tion wakeup does pre isely this. when some y list visited earlier. i.

This is also like adding a waiting room to the restaurant. Generalize the oee sha k problem so that there are several servers. the number of ustomers in the restaurant on the average. You will need to modify resour e. how long after the losing time did the ustomers stay around. Generalize the lass so that at most some k lients an be using the resour e simultaneously. 2. Exer ises 1.verti es[i℄. Modify the restaurant simulation to report how many ustomers left disappointed.distan e are printed. You may .nish their journey. Finally the distan es to ea h vertex i from the vertex sour e as omputed in G.

Modify the oee sha k simulation and verify Little's law experimentally. but just keep tra k of how many lients are using the resour e. Suppose that on the average ea h ustomer spends t minutes in the store. how many ustomers will you expe t to see in the store? Little's law from queueing theory says that this number will be pt. Suppose every minute a ustomer enters a store with a probability p. 3. Then on the average. The law requires that no ustomers are turned away.nd it easier to do this if you do not keep tra k of whi h lients are using the resour e. and that the average is taken over a long (really in.

nite) time. Suppose further that tables in the restaurant an a ommodate 4 ustomeres. rather than individually. Thus. Assume that the tables are in a single line. i + 1 are adja ent. Write a simulation of su h a restaurant. so if a party of 5 arrives. the party must wait if two adja ent free tables are not available. . Suppose a group an have upto 5 members. More ode will be needed to make all the measurements. and run the simulation for relatively long durations to he k. So you should remove the apa ity he ks. all sizes equally likely. 4. Write a simulation of a restaurant in whi h ustomers an arrive in a group. then two adja ent tables must be allo ated. so tables i.

Basi ally. Do not distribute 350 You will have to de ide on how a table will be allo ated if several tables are free: this will ae t how qui kly you serve parties of 5 members. Modify the program so that it prints the shortest path from the sour e to the destination ity. as a sequen e of the numbers of the ities on the way. 5. for the shortest path program. Abhiram Ranade. in ea h vertex you must store information about where the . Have an additional ommand line argument whi h gives the index of a destination ity. 2011.

This will enable you to .rst y list arrived from.

gure out how the shortest path arrives into a vertex. re ursively. This requires a somewhat signi.

ant modi.

ation. De.

rather than making a vertex a simEntity. Modify the shortest path algorithm to use ity names instead of ity numbers in the input . she will know where she arrived from.ne a y list lass whi h is a simEntity. The y list obje ts should ontain information about whi h ities they travel between. 6. Now when a y list arrives into a ity.

Consider the gates des ribed in Exer ise 14 of Chapter 5. Build a simulator for a ir uit built using logi gates. Spe i. A gate takes as input values 1 or 0. the output value is reliably available only after its delay. You should allow the user to build the ir uit on the graphi s window.le. However. and produ es output values a ording to its fun tion. 7. You should also allow a delay Æ to be entered for ea h gate.

Then the new orre t value will appear at the output only at time t + Æ. suppose some input value hanges at time t. During the period from t to t + Æ the value at the output will be unde. Suppose this will ause the output value to hange. ally.

ned. For this you should use the value NAN supported as a part of the header .

The value NAN represents \unde.le < math>.

This value behaves as you might expe t: do any arithmeti with it and the result is NAN.ned value". a tually the name is an a ronym for \Not A Number". .

what delays they fa e at dierent points. Is it possible to pinpoint the reason? Is it then possible to state the best ure to the problem: that you need to build an extra runway.Chapter 22 Simulation of an airport Suppose there are omplaints about eÆ ien y of an airport in your ity: say ights get delayed a lot. bigger airport? A simulation of the airport and how it handles air raft traÆ an very mu h help in making su h de isions. and al ulate the average delay for the new on. you simply build another simulation in whi h the extra gate is present. The simulation will take as input information about the runways and other fa ilities on the airport. It will then determine what happens to the air raft as they move through the airport. and about the air raft arriving into the airport from the rest of the world. or perhaps just build a ompletely new. The average of these delays is perhaps an indi ator of the eÆ ien y of the airport. or some extra gates. To answer questions su h as: how mu h will an extra gate (or runway or whatever) help.

guration. In addition to textually des ribing what happens to ea h air raft as it progresses through the airport. An animation is possibly easier to grasp { perhaps seeing the air raft as they move might dire tly reveal what the bottlene ks are. The . it is also desirable to show a graphi al animation in whi h we an see the air raft landing. taxiing or waiting at gates.

doubtless you have to throw away many details. We will begin by des ribing the airport we want to simulate and the rules under whi h the airport operates. On the other hand. of any entity. Then we give the general stru ture of a possible implementation. the more details you in orporate into your model. or a mathemati al model. the more a urate it is likely to be. we will design a program to simulate a fairly simple airport. Other fa tors that are perhaps less important are the pla ement of auxiliary servi es (e. Other fa tors that perhaps annot be ignored in lude the number of gates at whi h air raft an park to take in and dis harge passengers. if the details are hosen arefully. the number of runways in the airport is of prime importan e. In this hapter.rst step in building a simulation is to make a omputer model of the relevant aspe ts of the system being simulated. An important 351 . and so annot be ignored. models with relatively few details might also be useful. In general.g. However. so that may be ignored in our simulation. When you make a omputer model. A trivial example: the olour of the airport building is irrelevant as far as its ability to handle traÆ . air raft hangars) and traÆ asso iated with these servi es and how it might interfere with air raft movements. the layout of the taxiways that onne t the runways and the terminals.

Do not distribute 352 Figure 22. 22.1: Airport layout with planes problem in simulating omplex systems su h as an airport is deadlo k. We dis uss how deadlo ks an be dealt with in real life and in programs. Abhiram Ranade. 2011.1 Airport on.

guration and operation The on.

As you an see there are three air raft waiting. 1. There are bran hes going o the main taxiway to the gates. The long horizontal line at the bottom is the main taxiway. and 3. running lo kwise over itself to end in the top right orner. starting in the top left orner. at gates 0. The other lines are taxiways. The small triangles are meant to represent air raft. We will all this the main path. In our model of the airport. for simpli ity. Indeed. and the nearly verti al segments on the sides we will refer to as the left and right taxiways respe tively. we will only onsider the runways. If you ignore the bran h taxiways. taxiways. the runways and the other taxiways onstitute a single long path. So in this airport there are meant to be 10 gates. we will require that the main path be used in the lo kwise dire tion. Thus the runway starting at the top is the landing runway and the runway ending at the top right is the takeo runway. and gates for simpli ity.guration of our airport shown in Figure 22. but they are supposed to be present at the end of these short bran hes. whi h we will number 0 through 9. right to left. We have not shown the gates. The bran h taxiways going to the gates are expe ted to be used in both dire tions. Our on. and three others on the runway and taxiways. The two rossing lines at the top are two runways.

ex ept for the interse ting runways.guration is rather simplisti . Interse ting .

then permission an be granted to only one. and the taxiways and gate pla ements are more elaborate. The air raft then waits at the gate for a ertain servi e time. if two air raft request permission to use the runway (either for take o or for landing) at the same time. Do not distribute 353 runways are not rare. This entire pro ess has to be ontrolled by the airport authorities so as to ensure safety and eÆ ien y. so we will further require that if the initial half of the take o runway ontains an air raft then there should be no air raft in the initial half of the landing runway. In order to perform a simulation we need to know the pre ise s heduling strategy and gate assignment proto ol used by the airport.g. 22. as will be the ase when they are landing or taking o. the operation of an airport an be des ribed as follows. say to minimize the average delay. At a high level. This de ision will have to be taken by the air traÆ ontrollers. 2011.1 Safe operation rules The gist of the safety requirements is: air raft movement should be planned so that at all times air raft are well separated from ea h other. the runways interse t in the initial portion. e.2 S heduling strategy The exa t s hedule a ording to whi h air raft land and takeo and even move around while on the airport is de ided by the air traÆ ontrollers at the airport. In general. For example. and vi e versa. When an air raft arrives it must be assigned a gate at whi h it is to wait. Abhiram Ranade. or some weighted average delay with the weights being the priorities of the dierent air raft. A ertain minimum separation is required even as air raft are taxiing. by the way { in fa t the Mumbai airport has interse ting runways. The separation between air raft must be larger when they are travelling at high speeds. 22. But we need an even stronger half-runway-ex lusion rule be ause our runways overlap. After that the air raft taxies to the runway and takes o. So we will in fa t require that there be at most one air raft on ea h runway at any instant. But of ourse both the runways in Mumbai an be used for takeos as well as landings. ea h air raft may have its preferred gates at whi h it would like to wait.1. Another issue on erns gate allo ation. Su h de isions will be made so as to a heive ertain goals.1. They must obey the safe operation rules and in addition resolve on i ting requests. whi h is our inspiration for in luding them. As shown. Ea h air raft lands and taxies to a gate. For our simulation we will use a very simple .

rst ome .

we will assume that ea h air raft requests permission from the traÆ ontroller for ea h a tion it needs to perform. then permission is granted to the air raft whi h asked earliest. If several air raft ask permissions to perform a tions whi h require a ommon resour e (say the runway). 1 An air raft must begin its des ent mu h earlier than its landing time. However our . just as it be omes ready to perform the a tion. and on e the des ent has begun. Basi ally. For example. and the other air raft must wait. we might de ide to give higher priority to landings than takeos be ause it is easier for a plane to wait on ground that wait midair! This is explored in an exer ise.rst served s heduling strategy. Of ourse many other strategies are possible. the landing annot be postponed in normal ir umstan es.

rst ome .

rst serve strategy may require a ight arrival to be delayed. So to make this more realisti . we an assume that we are given 1 .

we are given the times required by an air raft to traverse ea h segment of the taxiway and the runways. we will assume that all air raft an wait at all gates. This assumes that the times are identi al for all air raft. First. 22. Abhiram Ranade.3 Simulator input and output The input to the simulator is of two kinds. Do not distribute 354 As to gate allo ation. and say the least numbered free gate will be allo ated. 2011.1. and this is of ourse a simpli.

and then take o and leave. For ea h air raft. ation. When designing an animation.g. an air raft arrives or leaves or stops at its gate? For simpli ity. Next.e. and the servi e time. or only when something interesting happens. (b) a text re ord of the times at whi h these events happen. Do we show it every se ond. i. The primary output from the simulator will be: (a) an animation of the air raft as they enter the airport. e. we wil assume the state is to be shown after every unit time interval. whatever the unit time we de. the amount of time the air raft needs to wait at a gate. halt for the required time. or every minute. we are given the arrival time. move to a gate. we need to de ide how frequently will we show the state of our airport. we are given the data about arriving air raft.

ne in the program. we may require several derived outputs. Let us de. In addition.

In fa t.3). We will have a plane lass to represent air raft. 22. The main idea is to break runways and taxiways into segments and make ea h segment a resour e (Se tion 21. Just as ustomers moved through the restaurant or the oee shop a quiring and releasing resour es and waiting. So the event driven approa h will also be onvenient. Here is how we will enfor e safe operation rules. and thus by hoosing suÆ iently long segments we an keep the air raft well separated. instead the s heduling will be done by the ode in the plane lass. so will the planes. and the Exer ises ask you to build a simulation using this approa h. We will not expli itly represent air-traÆ ontrollers. we will dire tly use the simEntity and simQueue lasses we developed for the restaurant simulation. so that the air raft an a tually delay the arrival to suit our omputed s hedule if needed. we will have the ee t of the ontrollers permitting the planes to move and allo ate gates. Sin e we are expe ted to show what happens at ea h instant of the simulation. .2 Implementation overview We an use either a time driven or an event driven approa h. By suitably reating resour es whi h the planes must reserve. The entities will be of ourse be the air raft. Note however that at ea h instant only very few air raft will be a tive. So we might be required to ompute the average delay. Su h analyses and extensions are left to the Exer ises. and of ourse enfor e safe operation rules. This is what we use here. This way there an be at most one air raft on ea h segment. The two runways will be separate the landing times well in advan e.ne the delay of an air raft to be the additional time it spent over and above when it ould have departed had the airport been ompletely empty. a time driven approa h might appear suitable. Our simulation will in fa t substantially resemble the restaurant or oee sha k simulations from Chapter 21. An air raft must reserve a segment before moving on it. The division into segments will be as follows.

This lass will inherit from the resour e lass so that it an a t like a resour e. We will onstru t a taxiway lass whi h will represent taxiways. we will require it to reserve a . To implement half-runway-ex lusion we will use the following tri k. the main horizontal taxiway will be split into 11 segments. Sin e there are 10 gates. 2011. Abhiram Ranade. The bran h taxiways will onstitute separate segments by themselves. The main taxiway will be broken up into segments at the points where the bran h taxiways leave from it. and so will the the left and right taxiways. Whenever a plane needs to land or take o. Do not distribute 355 segments.

and if so reserve it. During this period as well as during the period that it goes ba k to the main taxiway it will not release its reservation on bran h taxiway i. We will model a plane waiting at gate i by having it wait at the end of bran h taxiway i. The plane will traverse this taxiway. This a tion takes pla e when the requesting plane is on the . This models the onstraint that two planes will not use the same gate at the same time. this will ensure that only one plane an take o or land at the same time. We will not represent the gates expli itly. we simply release rwCommon as soon as the plane gets to the middle of the landing runway! Same thing for a plane taking o { it will also release rwCommon when it gets to the middle of the takeo runway. To enable this. Sin e only one plane an reserve any taxiway. we want to allow another plane to start taking o. After a plane has landed and traversed half the runway. go to the end and wait for its servi e duration. titious rwCommon taxiway in addition to reserving the landing or takeo runways respe tively. To allo ate a gate we merely examine all the bran h taxiways and determining if any is free.

The main program also reads in the arrival and servi e times of the planes.rst segment of the main taxiway.3). These are reated by the main program. and the taxiway rwCommon.0. // urrent time is 0.2 and 21.1000. taxiway *rwCommon.0. 22.1 Main program and main data stru ture The main data stru ture in the program is a ve tor of all taxiways. ve tor<taxiway*> TAXIWAYS.2. } getCli k(). initialize_sq_with_arriving_planes(). These obje ts are inserted into simQueue. and reates orresponding plane obje ts. loseCanvas(). to be woken up at their arrival times. All the reservation a tions happen as a part of the wakeup method of the plane lass. After this we let the simulation unfold itself by alling simQueue::pro ess till empty.1000). . just as all the simulation logi in the restaurant and oee sha k simulation was a part of the wakeup method in the ustomer lass (Se tions 21. onfigure_taxiways_and_runways(). simQueue::pro ess_till_empty(). int main(){ initCanvas("Airport Simulator".

To use simQueue we must of ourse in lude the header . as given below. Do not distribute 356 The fun tion onfigure taxiways and runways sets up the data stru tures to represent taxiways and runways. 2011. The fun tion initialize sq with arriving planes reates the planes. Abhiram Ranade. whi h also dis usses the taxiway lass in detail. We dis uss this fun tion in the next se tion.

lass taxiway : publi Line. while(arFile >> arrivalT){ arFile >> servi eT.yb). traversalT(trT) { stepsize = sqrt(pow(xa-xb. } }. plane *p = new plane(id++. } int arrivalT. float yb. int trT) : Line(xa. void initialize_sq_with_arriving_planes(){ ifstream arFile("arrivals. simQueue::insert(arrivalT. // Planes are assigned numbers.ya. taxiway(float xa. 22.h from the last hapter. and the planes must be able to reserve them.le sim.3 The taxiway lass Instan es of the taxiway lass must serve two purposes: they must be visible on the s reen as lines. servi eT.2)+pow(ya-yb. double stepsize.o while ompiling.p). } The plane lass is dis ussed later. So it is natural to derive the taxiway lass from the Line lass and the resour e lass of the pre eding hapter.servi eT).2))/traversalT. and also use sim. publi resour e{ publi : int traversalT.txt"). int id = 1.arrivalT. The taxiway onstru tor . float xb. float ya.xb.

In onstru ting a taxiway we also provide the time required to traverse it in some hypotheti al time units. . Ideally we should distinguish the on-s reen line from the real taxiway. For simpli ity we have assumed that the on-s reen taxiway and the real taxiway will have same oordinates on the s reen as well as the ground (say the units have been onveniently sele ted). and provide details about the real taxiway separately. Sin e we know the length of the taxiway we al ulate how mu h an air raft moves forward ea h (hypotheti al) step when on this taxiway { this information is needed to perform the animation.rst reates the Line representing the taxiway on the s reen.

This will set the owner of the taxiway (derived from resour e) to NULL. indi ating that initially the taxiway is unreserved. The segments of the main path will onstitute the . Abhiram Ranade. so a all with no arguments will be inserted by the ompiler. 2011. Do not distribute 357 Note that the resour e onstru tor is not expli itly alled. The fun tion onfigure taxiways and runways will instantiate taxiways to reate the main path and the bran h taxiways.

tBT).RW2Y1. (int) (TWX1+(i+1)*twXdisp). (int) (TWY1+(i+1)*twYdisp).tRW). (int) (TWY1+(i+1)*twYdisp).0.RW2X2. } TAXIWAYS[3+nGates℄ = new taxiway(TWX2. TWYT. (int) (TWY1+(i+1)*twYdisp).RW2Y2. for(int i=0. // right taxiway float twXdisp = ((float)TWX2-TWX1)/(nGates+1). and the names tRW et . TAXIWAYS[0℄ = new taxiway(RW1X1. For larity of understanding we use the onstant nGates in the ode instead of the number 10. ++i){ // main taxiway: 11 segments TAXIWAYS[2+i℄ = new taxiway((int) (TWX1+i*twXdisp). } for(int i=0.tVT).TWY2. tBT). ++i){ // bran h to gate TAXIWAYS[5+nGates+i℄ = new taxiway((int) (TWX1+(i+1)*twXdisp). are onstants indi ating the geometri oordinates of the appropriate taxiways. void onfigure_taxiways_and_runways(){ rwCommon = new taxiway(0.0. tMT).RW1Y2.TWY1. (int) (TWX1+(i+1)*twXdisp). // takeoff runway for(int i=0. .0).RW1Y2. are onstants indi ating the time to traverse the appropriate taxiways. float twYdisp = ((float)TWY2-TWY1)/(nGates+1).RW2Y1.tVT). // ommon part of runways. the bran h taxiways going toward the gates the next 10.RW1X2. // landing runway TAXIWAYS[1℄ = new taxiway(RW1X2. // left taxiway TAXIWAYS[4+nGates℄ = new taxiway(RW2X1.rst 15 elements of the array TAXIWAY. i<nGates. TWYT.TWX1.RW1Y1. (int) (TWY1+i*twYdisp). i< nGates.RW2X1. } } The names RW1X1 et . ++i){ // bran h from gate TAXIWAYS[5+2*nGates+i℄ = new taxiway((int) (TWX1+(i+1)*twXdisp). and the bran h taxiways oming ba k from the gates the last 10.0. (int) (TWX1+(i+1)*twXdisp). i<= nGates.tRW).

2011. We ould have de. an air raft must appear on the s reen as a part of the animation. The air raft are the entities in the simulation. In addition.4 The plane lass 358 The air raft are implemented using a plane lass. and so plane must inherit from the simEntity lass of the previous hapter and must provide a wakeup member fun tion. Do not distribute 22. our air raft appear on the s reen as turtles. So we inherit from the Turtle lass as well. Indeed. Abhiram Ranade.

Through su essive exe utions of the fun tion wakeup. When it omes to the end of a segment. If the air raft is in the middle of a taxiway. it will need to . What state do we need to maintain? You will realize that the a tion to be taken by the air raft depends essentially upon its position. The wakeup fun tion of the plane lass onstitutes the heart of the simulation. As dis ussed in Se tion ??. but that is left for the exer ises. it merely needs to move forward whatever distan e it an move in one unit time. make requests to allo ate gates. request ex lusive a ess to taxiways so that separation is maintained. we must maintain some state in ea h plane obje t so that when wakeup is alled we an de ide what a tion to perform based on the state. wait at the gates and so on.ned a more air raft like visual appearan e by using the polygon lass. the air raft will move forward along the taxiways.

Further. It will also need to release the segment on whi h it is urrently lo ated.rst reserve the next segment (if any) and then turn to align with the dire tion of that segment. some spe ial a tions need to be taken if the air raft is on spe i.

indi ating that the plane is yet to enter the airport. if so.g. On reation. In addition. and timeToSegmentEnd. we must know how mu h the air raft has travelled on the segment. this is set to -1. In timeToSegmentEnd we store the number of steps we need to move forward before we need to worry about turning or reserving the next segment. In data member segment we store the index of the segment (in the ve tor TAXIWAY) on whi h the plane is urrently present. In addition. e. We do this using 2 data members in ea h plane obje t: segment. if the air raft is on the segment before the main taxiway. segments. whi h gate. So learly we need to keep tra k of whi h taxiway segment the air raft is on. we need to keep tra k of whether the air raft has been allo ated a gate. and . then it must also ask for a gate to be allo ated.

nally whether it has .

The latter is initialized to false. or is yet to begin the servi e. The former is initialized to a large value so that it indi ates that a gate has not been allo ated. This leads to the following de.nished waiting for servi e. and for the latter. a boolean. For the former we use an integer data member gate. served.

servi eT(st) { . lass plane : publi Turtle. publi : plane(int i. bool served. int at. publi simEntity { int id. int arrivalT. int servi eT. int st) : id(i). int gate. arrivalT(at).nition of plane. int segment. int timeToSegmentEnd.

gate = 10*nGates. // urrently before the landing runway. getGate().g. } void void void bool wakeup(). penUp(). }. segment = -1. Abhiram Ranade. hide(). Do not distribute 359 timeToSegmentEnd = 0. e. enter(taxiway *ptw).size()-1 the takeo runway. To refer to su h segments transparently we de. pro ess_entry_to_next_segment(). index = 0 indi ates the landing runway. 2011. Note that some segment index values are spe ial. // very large number to indi ate no gate allo ated served = false. and index = TAXIWAYS.

we are entering a new segment. } . else{ if((segment == landing || segment == takeOff) && timeToSegmentEnd == TAXIWAYS. --timeToSegmentEnd. } forward(TAXIWAYS[segment℄->stepsize). // starting index of taxiways to gates fromGateStart = 5+2*nGates.at(segment)->traversalT/2){ rwCommon->release(). requestGate = 1. 22.1 The fun tion wakeup At a very high level. If timeToSegmentEnd is not zero. landing = 0. we generally only move forward in the urrent segment.4. but this an ee tively be used to express that the air raft is yet to arrive into the airport. If timeToSegmentEnd has be ome 0. We will of ourse not use PRELANDING = -1 to index TAXIWAYS. } return. simQueue::insert(1. preFirstGate = 2. takeOff = toGateStart-1}. void plane::wakeup(){ if(timeToSegmentEnd == 0) pro ess_entry_to_next_segment(). and might need to take some de isions.this). // starting index of taxiways from gates enum segmentindi es {preLanding = -1.ne the following names for later use. the wakeup member fun tion is simple. preTakeOff = toGateStart-2. onst int toGateStart = 5+nGates.

we must release rwCommon. the plane may either have to wait be ause ertain resour es are not available. The plane may be in a position to immediately exe ute the a tions of the next state. After those a tions are performed. Here is the . the plane puts itself ba k in simQueue to be woken up again at the next step. In ea h ase. This is what the above ode does. and so it will have to reexe ute the ode for wakeup. At the end of the move. The ode in this onsists of a long sequen e of ases depending on the state of the plane. unless we are on the landing segment or the takeo segment. Do not distribute 360 If timeToSegmentEnd is not 0. the easiest way to do this is by queueing itself in simQueue for the urrent step itself. a ertain set of a tions are performed. Remember that as we pass the middle of these segments. we move forward by the stepsize determined for the urrent taxiway. The fun tion pro ess entry to next segment is given next. 2011. Abhiram Ranade. or if the resour es may immediately go to the next state.

void plane::pro ess_entry_to_next_segment(){ if(segment == preLanding){ if(!TAXIWAYS[0℄->reserve(this)) TAXIWAYS[0℄->await(this). Servi e time " << servi eT << endl.rst part of the fun tion. else if(!rwCommon->reserve(this)) rwCommon->await(this). enter(TAXIWAYS[0℄). show(). segment = 0. } } // to be ontinued This part des ribes what is to be done for the . s heduled arrival " << arrivalT << ". else{ simQueue::log()<< "Plane " << id << " lands.

The member segment is set to 0. If this is not immediately available. i.rst time wakeup is alled. Else it pro eeds to a quiring rwCommon.e. i. then it prints out a status message. when the plane is yet to land.e. indi ating it has landed. then the plane waits for it by alling the await fun tion. The plane must a quire the landing runway. If both these taxiways are available. And . TAXIWAY[0℄.

the plane awaits its release. However. This fun tion aligns the plane with the line asso iated with the segment. and sets timeToSegmentEnd to be the time required to traverse this segment. the a tual exe ution is more omplex: when the resour e is released.g. If any of the resour es needed. e. An important point should be noted. the plane is put ba k on simQueue for exe uting at the urrent timestep itself (Se tion 22. It might be tempting to think that the exe ution of pro ess entry to next segment \suspends" at the point of alling await and resumes when the resour e be omes available. rwCommon is not available. Finally.4. the wakeup fun tion is .2).nally the member fun tion enter is alled to do some bookkeeping asso iated with entry to a segment.

i.e. . no spe ial a tions are needed. The next all to wakeup happens when the plane arrives at the end of segment 0. we simply need to reserve the next segment and so on. say rwCommon->reserve(this) will turn out true. ex ept that this time the resour e will be seen to be available. In this ase. into pro ess entry to next segment. and hen e the else part will be entered. The fun tion exe utes from the beginning and tra e the same path as before.rst alled.

2011. Abhiram Ranade. Do not distribute 361 It is onvenient to organize the ode of pro ess entry to next segment so that the spe ial ases ome up .

and if not.at(segment+1)->await(this). as will be seen in the de. segment++. else if(!TAXIWAYS. We annot simply wait on a resour e.at(segment)->release().rst. else{ TAXIWAYS. be ause we are waiting for any of the gates to be available. where the plane must make a request for a gate.at(segment+1)->reserve(this)) TAXIWAYS. // pro ess_entry_to_next_segment ontinued else if(segment == requestGate){ if(!getGate()) simQueue::insert(1. we retry after 1 step. So the next spe ial ase on erns entry to segment 1.this). enter(TAXIWAYS.at(segment)). } } Here we he k to see if a gate is available.

to i. Note that the release must happen only after the next segment has been a quired. enter(TAXIWAYS[segment℄). simQueue::insert(servi eT. the plane releases the urrent segment and enters it.4. If some gate i is available. The Exer ises ask you to explore how to avoid this repeated he king. The next ases are about turning towards the gate. enter(TAXIWAYS[segment℄). served = true. segment = toGateStart + gate. and returning ba k to the main taxiway. } else if(segment == toGateStart + gate){ // at end of taxiway to gate? if(!served){ simQueue::log()<< " Plane " << id << " at gate " << gate << " will wait for " << servi eT << endl. waiting. the fun tion getGate sets the member gate.3). // wait for servi e } else{ segment = fromGateStart + gate. } } else if(segment == fromGateStart + gate){ // at end of from taxiway? .this). If that segment is available. // pro ess_entry_to_next_segment ontinued else if(segment == preFirstGate + gate){ // about to turn to gate? TAXIWAYS[segment℄->release(). After that the plane ontinues taxiing and tries to move to the next segment.nition of getGate (Se tion 22. Hen e we need to a tively try again.

Abhiram Ranade. So we set wait to simulate the servi e time and set it true. The next ase on erns the situation when wakeup is alled with segment == toGateStart + gate. this is when we are at the end of the bran h segment. After we have just turned into the bran h taxiway. segment = preFirstGate + gate + 1. we set gate to a large value. enter(TAXIWAYS[segment℄). else{ TAXIWAYS[toGateStart + gate℄->release(). } The ondition he k segment == preFirstGate + gate will su eed if the urrent segment is the one at whi h we need to turn towards our assigned gate. This is easily seen to orrespond to the segment toGateStart + gate. we start our journey towards the main taxiway by entering the bran h taxiway going away from the gate gate. The . Note that on initialization. gate. So we enter that. so that the ondition he k would have no han e of su eeding until we gave a valid value in gate. we move to a bran h taxiway. Do not distribute } 362 if(!TAXIWAYS[preFirstGate + gate + 1℄->reserve(this)) TAXIWAYS[preFirstGate + gate + 1℄->await(this). If served was already true. This orresponds to segment fromGateStart + gate. If the he k su eeds. the data member served would be false. Clearly. 2011.

nal ase is when we have rea hed the end of the bran h taxiway going towards the main taxiway. segment fromGateStart + gate. The . In this ase we must enter the main taxiway. after releasing the reservation on the taxiway going towards our allo ated gate. As we noted. this will enable other planes to use this gate later. i.e.

whi h applies to all non-spe ial segments. hide(). enter(TAXIWAYS[segment℄). } When leaving the pre-takeo segment.nal two spe ial ases on ern the takeo and pre-takeo segments. else if(!rwCommon->reserve(this)) rwCommon->await(this). rwCommon." << endl. we must not only reserve the takeo segment but also And when we leave the takeo segment. simQueue::log() << " Plane " << id << " left. . else{ TAXIWAYS[segment℄->release(). // pro ess_entry_to_next_segment ontinued else if(segment == preTakeOff){ if(!TAXIWAYS[takeOff℄->reserve(this)) TAXIWAYS[takeOff℄->await(this). the default ase. ++segment. } } else if(segment == takeOff){ TAXIWAYS[segment℄->release(). Finally. we must print out a message and hide ourselves.

22. timeToSegmentEnd = ptw->traversalT.getX(). fa e(lineend. Position lineend = ptw->getEnd(). after releasing the urrent segment. moveTo(linestart.2 The fun tion enter void plane::enter(taxiway* ptw){ Position linestart = ptw->getStart(). linestart.getY()).getY()). the plane . Do not distribute 363 // pro ess_entry_to_next_segment ontinued else{ // ordinary segment if(!TAXIWAYS[segment+1℄->reserve(this)) TAXIWAYS[segment+1℄->await(this). 2011. simQueue::insert(0.4. enter(TAXIWAYS[segment℄). } } } // end of fun tion We reserve the next segment and enter it. Abhiram Ranade.getX(). else{ TAXIWAYS[segment℄->release().this). lineend. } When entering a segment. ++segment.

} Remember that the taxiway going towards gate i is to be reserved to simulate a quisition of gate i. so this step is really not needed. Then the ounter timeToSegmentEnd is initialized to the time required to traverse this segment.rst positions itself at the beginning of the line orresponding to the segment.++i) if (TAXIWAYS[toGateStart + i℄->reserve(this)){ gate = i. 22. the positioning is required. gateAllo ated = true. Most of the time the end of the last segment and the beginning of the next segment will be identi al.3 The fun tion getGate bool plane::getGate(){ for(int i=0. After that the plane orients itself by fa ing the end of the line representing the taxiway. . return true. and for this it inserts into the queue to be woken up immediately. } return false.i<nGates. This taxiway is represented by segment toGateStart + i. Now the plane is ready to travel on the segment. However. when the plane lands.4.

364 Abhiram Ranade. However we have to be areful in implementing the half-runway-ex lusion rule.5 shows ars deadlo ked on roads in a ity. It turns out that deadlo ks will not arise if we observe the following dis ipline in reserving rwCommon. Figure 22. A deadlo k is possible on a ir ular taxiway if every segment ontains a plane whi h wants to move forward. as you an see. Do not distribute Figure 22. In our airport it would seem that the taxiways do not form a ir ular path. A landing air raft must . Noti e that in this ase no entity an make progress. Note that the roads are one ways.2: TraÆ deadlo k in a ity 22. The ars are waiting for the spa e ahead of them to be ome empty.5 Deadlo ks A deadlo k is a te hni al term used to des ribe a system in whi h one entity e is waiting to reserve a resour e held by entity e whi h in turn is waiting to reserve a resour e held by and entity e and so on. but it never will. as shown. be ause all are waiting for ea h other. till some entity en in this sequen e is waiting to reserve a resour e held by e . 2011.

rst reserve the landing runway and only then rwCommon. Similarly a plane taking o must .

then it prevents take os unne essarily until su h time as it reserves the landing runway. You an see that this is a good strategy: rwCommon being a pre ious resour e must be reserved last. If a plane reserves rwCommon and annot reserve the landing runway.rst reserve the takeo runway and only then rwCommon. On the other hand. More formally. as the exer ise asks you. you should be able to prove that if this poli y is used there an be no deadlo k. if landing planes as well as planes taking o reserve rwCommon .

1 2 3 1 .rst. The exer ises invite you to explore this possibility. then it is possible to reate a deadlo k by arefully onstru ting the arrival sequen e of the planes.

Exer ises 1. Modify the simulation program to print out the average air raft delay. 2. Do not distribute 365 22. we should really pass a referen e to it to the plane lass in whi h it is used. Abhiram Ranade. As dis ussed in Appendix B. Instead of making TAXIWAYS a global variable. 2011. use of global variables is not re ommended.6 On Global variables vs. De. referen e variables This is the only hapter in whi h we have used a global variable.

we must he k whether no plane will want to land during the interval in whi h the departing plane will use rwCommon. In that ase the entity may await its release. Hint: perhaps you an reserve the landing runway and rwCommon a bit earlier than needed? 4. 6. the plane retries after 1 step. Spe ifi ally. When any of the obje ts be omes available. 3. Show that our strategy of reserving resour es ensures that there is no deadlo k. i. ea h of whi h an be either reserved or unreserved. one of the unreserved obje ts must be allo ated. If all obje ts are urrenly reserved. It will be more eÆ ient if the plane an await the release of any gate. Thus. en where ei is waiting for a resour e urrently held by entity ei n. i. 5. then the reserve request is deemed to fail and should thus return false. show that at every step some air raft will make progress.e. : : : . if a gate is not urrently available. The program given in the text uses so alled busy waiting to allo ate gates. Suppose we wish to ensure that as mu h as possible. while granting rwCommon to a departing plane. that should get reserved for the waiting entity. and that there will not exist entities e .ne a better plane lass in whi h the on s reen image looks like an air raft rather than a triangle. an air raft must land at its arrival time. On a reserve request. Use this in the simulation ode. the requesting entity should be set as its owner.e. Devi e a good me hanism to do this. Develop a lass to represent su h a resour e group. Suppose we reserve rwCommon . A resour e group models a sequen e of obje ts.

Constru t an input sequen e (the .rst and then the take o or landing runways.

if any. Show a visual simulation of the algorithm. Implement this. 7. i. the 0 +1 mod 1 . a turtle should move along ea h edge as if it were a y list.le arrivals. Instead.e.4. Consider the shortest path algorithm of Se tion 21. 8. suppose we will allow a plane to move a ertain stepsize at ea h step while keeping a ertain safe distan e behind the plane ahead.e. The other rules must still be followed.txt) su h that there is a deadlo k. i. Suppose that we are also given the geometri oordinates for ea h vertex of the graph. Suppose we do not want to divide the taxiway into segments and require that there is at most one air raft in ea h segment.

2011. Do not distribute 366 half-runway-ex lusion rule and the rule that there an be at most one air raft on ea h runway at any instant. Abhiram Ranade. Simulate another airport on. there an be only one air raft on any bran h taxiway. 9. Also.

.guration of your hoosing.

3 for the one dimensional ase. While. ompute the on. What are the lengths of the sides of the box? If u . We have already studied NRM in Se tion 7. After studying NRM for multiple dimensions.Chapter 23 Non-linear simultaneous equations Suppose you want to onstru t a parallelopiped box of volume 1010 m . 2(u u + u u + u u ) = 700 and u + u = 22 . Indeed it is fair to say that solving non-linear simultaneous equations is bit of an art. but unfortunately these equations are non-linear! In Se tion ?? we saw how to solve linear simultaneous equations. we will onsider a more elaborate problem: given a hain of links of dierent lengths. We have 3 equations in 3 unknowns. On e su h strategy is the Newton-Raphson method (NRM). there are some strategies whi h seem to often work. u denote the side lengths in m. learly we have u u u = 1010. Its generalization to multiple dimensions is pre isely what we need and we will study it in this hapter. surfa e area 700 m and having a base whose diagonal is 22 m. but this problem is mu h more diÆ ult. there is no single guaranteed method for solving non-linear equations in many variables. u .

guration in whi h it hangs if suspended from some .

The exer ises give more appli ations of NRM in multiple dimensions. We will see that NRM solves this problem ni ely. 3 2 1 3 2 3 2 1 1 2 2 1 2 2 3 1 2 2 23.xed pegs. NRM is used to .1 Newton-Raphson method in many dimensions 3 In one dimension.

e. i.nd the root of a fun tion f of one variable. .

We are now given n fun tions f . : : : .nd u su h that f (u) = 0. fn ea h of n variables. and we want to . The higher dimensional ase is a natural generalization.

our equations for the box problem an be stated in this form as follows: f (u . Indeed. but then we an treat what is on the left hand side as a fun tion of the unknowns. u .1) f (u . 1 1 1 1 1 2 3 2 1 2 3 3 1 2 1 1 2 2 3 2 3 2 1 3 1 2 3 1 367 3 2 2 2 3 1 .nd their ommon root. u ) = 2(u u + u u + u u ) 700 = 0 (23. : : : . f . u . this is really the same as solving simultaneous. un su h that fi(u . u . un) = 0 for all i. possibly non-linear equations.e. a set values u . i. Any equation in n unknowns an be written so that the right hand side is 0. u ). u ) = u + u 484 =0 (23. : : : . of f . u ) = u u u 1010 =0 (23.3) Indeed the ommon root u = (u . As you might see. f will pre isely give us the side lengths of the box we want to onstru t. u .2) f (u .

2011. we have our urrent guess for the values of the unknowns. 368 Abhiram Ranade. NRM in many dimensions pro eeds iteratively. In ea h iteration. Note that in this interpretation the errors an be positive or negative. Do not distribute An important point to be noted is that ea h fun tion fi an be thought of as the error for the orresponding equation. Our goal in solving the equations is to make the error zero. We then try to . As in one dimension.

Then we have f (u ur . sin e f is a fun tion of many variables. we know that f will hange in proportion to u and the derivative of f with respe t to u . u ur = 10 and u ur = 5. : : : . so that we (hopefully) get loser to the root. un to add to these values so as to get our next guess u next. If we make a small in rement u in u . and that be omes our next guess. un ur. u ur ) = 10. We will use our box problem as a running example for explaining the method. f (u ur . We he k if we our new values are lose enough to the ( ommon) root. We will use u . Now this is simply the one dimensional ase. all of whi h we are keeping . : : : . We then make the required hange in the unknowns. u ur . u ur ) = 16. un to denote the unknowns. Suppose for this problem we have guessed u ur = 20. Otherwise we repeat. If so. we stop. A tually. u ur ) = 0. u ur .nd by how mu h ea h unknown should hange. Our goal is to determine what in rements u . For a minute onsider that we only want to make f be ome 0. Let their urrent values be u ur . : : : . unnext. f (u ur . and we only an hange u . u ur . : : : .

Further. we should really say. Thus the (additive) hange f in f will be approximately uf u . so we will write: 1 1 1 1 1 1 1 2 3 2 1 2 2 3 3 3 1 2 3 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 f 1 1 1 .xed ex ept for u . \the partial derivative of f with respe t to u ". the partial derivative must be evaluated at the urrent values.

f1 .

.

u u1 .

ur 1 (23. .4) But we want f next = f ur + f to be ome zero.

so perhaps we should hoose f = .

.

.

f .

.

f ur = 10. we know that u . Further.

= u u .

Thus we have: 1 1 1 1 1 1 1 2 3 ur ur 10 50u So we indeed hoose u = = 0:2. and the new value of f be omes 20:2 10 5 1010 = 0. = 50. In this ase. the error in the .2.2=20. The new value of u be omes 20+0.

4 generalizes as: 1 1 10 50 1 1 1 1 1 Think about hanging 1 . if we are allowed to vary all the variables. then equation 23. Things will not be this good in general.3 that we an expe t f to get loser to 0 than it was. Thus. But of ourse.rst equation has ompletely vanished. nothing really for es us to only hange u . but as you might remember from Se tion 7.

and then 2 and so on. Initially we are at ( 1 ur 2 ur 3 ur ).rst. In this movement. we have hanged . After hanging 1 by get to the point whi h we will all ( 1 ur 2 ur 3 ur ).

f1 .

.

From the new point we hange 2 by 2. 1. The hange that this auses in 1 is 1 by about u1 .

1 u u u u u u f about .

f1 .

.

u2 .

u u u u 2 total hange in 1 is approximately u f f1 u1 But the values at ur and ur 0 . 0. 0.

.

.

.

1+ u ur f1 u2 .

.

.

.

u f ur ur0 . u . assuming 1 2 are small.u 0 u2 are nearly the same. ur0 . u .

Do not distribute . 369 Abhiram Ranade. 2011.

.

f1 .

.

u u1 .

ur 1 .

f1 .

.

f1 .

.

f1 + u .

u2 + u .

u3 2 ur 3 ur Again. and. we want f1 = f1 ur .

try to pi k .

u2. u3 to.u1.

satisfy f .

f .

f .

f1 ur = 1 .

.

u1 + 1 .

.

u2 + 1 .

.

5) (23. u3 u1 ur u2 ur u3 ur (23.6) In a similar manner we will require.

the following.

as well. .

f .

.

f .

.

f .

.

u + u .

u + u .

u (23.7) f ur = u .

ur ur ur and .

.

.

f .

.

f .

.

f .

.

f ur = u + u .

u + u .

u (23.8) u .

u next. 0:283244. 5:06). 0:24. For these values we see that (f .8).1. 0.23.11) Solving this we get (u .7. whi h taken together are mu h loser to zero than (10. u ) = ( 0:52. Evaluating the urrent values of the fun tions and the partial derivatives we get: 10 = 50u + 100u + 200u (23. 2 2 1 3 3 1 2 2 2 3 1 1 2 2 1 3 3 2 2 3 3 3 3 1 2 1 3 2 3 1 1 2 2 3 1 1 2 2 3 3 23.23. u .1 The general ase In general we will have n equations: . u next = (19:48. ur ur ur Noti e now that u . So we have (u next. 10:24. 16).9) 0 = 30u + 50u + 60u (23. u are the only unknowns in Equations (23. f . 0:06).6.10) 16 = 40u + 20u (23. 0:327963). and in these variables the equations are linear! Thus we an solve them. u . f ) = (0:655554.

X fi .

.

uj fi (u ur . un ur ) = u . : : : .

and from these we an al ulate ujnext = uj ur + uj . 1 j (23. for all j . n). It is ustomary to. : : : .12) j ur We solve these to get (u .

onsider the above equations in matrix form. De.

ne an n n matrix .

f .

A in whi h aij = u .

De. uj .

b are known and we solve for u. Further. The matrix A is said to be the Ja obian matrix for the problem. : : : . ur Let u denote the ve tor of unknowns (u .ne an n element ve tor b where bi = fi (u ur . Then the above expressions an be written in the form A(u) = b in whi h A. un ur ). it is ustomary to de. un). : : : .

Then our next guess omputation is simply: unext = u ur + u Next we omment on when we should terminate the pro edure. un ur) and unext = (u next. : : : .ne ve tors u ur = (u ur . : : : . and how to make the . unnext).

rst guess. 1 i j 1 1 1 1 .

Note that this satis. This is be ause very lose to the root. Do not distribute 23.3) worked quite badly: it produ ed the \answer" (2. A standard way of doing this is to require that f + . In keeping with p our interpretation that fi is the error.1.2. On the other hand. this is more diÆ ult. the quantity (f . 10. 2011.1. we roughly plotted the fun tion and sought a point lose enough to the root. Newton's method works beautifully if we are already lose to the root.3 Initial guess Finding a good guess to start o the algorithm turns out to be tri ky. and even smaller if we use double to represent our numbers. 370 Abhiram Ranade. 11) work quite well. the equations su h as Equation (23.2 Termination We should terminate p the algorithm when all fi are lose to zero. In one dimension. fn ) is the ve tor error. fn is the 2-norm or the Eu lidean length of the ve tor error. : : : . we found for the box problem that a starting guess of (u . fn be ome smaller than some that we hoose.2659 -21.883 -20. 2 1 7 2 1 2 1 2 23. say = 10 if we use float. and f + . u .3692).1 very losely. For example. Note that these numbers satisfy Equation 23. It is often enough to satisfy only some of the equations.6) be ome very a urate. In multiple dimensions. One idea is to try to satisfy the equations approximately. an initial guess of (1. u ) = (9.

yi denote the oordinates of the left endpoint of link i. where the ith link has length Li . : : : .2 How a ne kla e reposes Suppose you are given a hain of n links. The other xi . What is the shape attained by the hain when it omes to rest. yn) whi h are known. Note of ourse that by Newton's third law. 0 0 23. n 1. Say the hain is hung from pegs at points (x . y ) and (xn. i = 0. thus the variables xi. n 1. y ) and (xn. yi are then the oordinates of the right endpoint. As dis ussed above.2.es the equations losely. 1 2 3 23. yi are the unknows we must solve for. : : : . (xi xi ) + (yi yi) Li = 0 (23.1 Formulation Let xi . yi must satisfy the following equations. and Fn is the for e exerted by link n 1 on the right peg). +1 0 +1 0 +1 0 2 +1 2 2 1 . we already know the values of (x . We are given the lengths Li of the links. where i = 0. In the next se tion. but surely we annot have negative side lengths! This points to another feature of non-linear equations: there may be multiple roots. hung in this manner? The links in the hain need not have equal lengths. and of ourse xi . we will have more to say on this. yn).13) We also need to onsider the for es on the links. Your iterative pro edure may not ne essarily take you to the orre t one. Suppose that Fi is the (ve tor) for e exerted by link i 1 on link i (F is the for e exerted on link 0 by the left peg. these are the oordinates of the pegs from whi h the hain is suspended.

we will assume that the weight is proportional to the length. i.2. also in the ounter lo kwise dire tion. Also we an arrange the for e values so that the total verti al for e on ea h link is 0. Balan ing the verti al omponent we get. vi). for all i: vi vi + Li = 0 (23. So ea h link i has a for e Fi a ting on its left endpoint. Be ause Wi is only verti al.15) are not linear. but in the ounter lo kwise dire tion. and h. vn to bear half of it. Suppose Fi = (hi . This torque is in the lo kwise dire tion. Further.e. The torque due to the horizontal omponent of Fi is simply the horizontal omponent times the verti al distan e to the horizontal omponent. To make a good guess. (23. there is its weight. Wi. For the ne kla e problem. onsidered in say the lo kwise dire tion. One way to do this is to ompute the total weight. The distan e to the line of the weight is (xi xi )=2. and (23. the latter exerts a for e of F on the former. and v . Hen e we do not have the negative sign. must be zero. However. we an write it as Wi = (0. It is mu h tri kier to try to balan e the torque. total for e on ea h link must be zero. i. 0 .2 Initial guess Making a good initial guess is vital for this problem. For this we need to onsider the right endpoint to be the enter. xn (noting that x . also ve tor. we have to make use of our \ ommon sense" expe tation about what the solution is likely to look like.15) Equations (23. Now balan ing the horizontal omponent we get hi hi = 0. On e we set this the other values of vi an be set as per Equations (23. Do not distribute if one obje t exerts a for e F on another. whi h a ts at its enter. 371 Abhiram Ranade. +1 +1 +1 +1 +1 +1 +1 +1 +1 +1 1 +1 1 +1 0 1 1 0 23. wi). yi) along a semi ir le whi h hangs from the pegs. yn . The horizontal for e h ould be set to 0 to begin with. we an expe t that the ne kla e to hang in the shape of a \U".13). vn. however. : : : . and so we will write wi = Li . So presumably we an set (xi . Further.14). But it turns out that the initial values as we have outlined here are enough to produ e a good answer. : : : . So we need to use the Newton Raphson method.e. Thus there are a total of (n 1)+(n 1)+1+(n +1) = 3n unknowns. Thus it is hi (yi yi) = h(yi yi). Remember that the torque due to a for e F equals the magnitude of the for e times the perpendi ular distan e from the enter to the line of the for e. and a for e Fi a ting on its right endpoint. When the hain is at rest. do note that in the oordinate system of our graphi s s reen y in reases downwards. and so the torque due to it is Li (xi xi)=2. The weight a ts downwards. and set v . Thus we get: h(yi yi) vi (xi xi ) Li (xi xi )=2 = 0 (23.15) apply to ea h link. Thus the number of unknowns and the number of equations mat h.14). vi (xi xi ). Thus for ea h link we have Fi Fi + Wi = 0. as well as the total torque.14) Finally we need to balan e the torque as well. The unknowns are x .13) and (23. xn are known) and similarly y . But the total torque. : : : . hi and vi are the horizontal and verti al omponents of Fi . 2011. so perhaps we should write wi as the y omponent. The torque due to the verti al omponent is similar. all these variables are identi al! Thus we ould write a ommon variable h instead of them. and thus we have 3n equations over all. our equations (23.

Abhiram Ranade.2. After ea h iteration. 2011.3 Experien e We oded up the algorithm and set the initial values as per the guessing strategy des ribed above. We then ran the algorithm. we plotted the ne kla e on. Do not distribute 372 23.

As you an see.guration on our graphi s s reen. the on.

guration qui kly seems to rea h a stable point.3 Remarks As you experiment with NRM you might noti e that the error norm (as de. and it got lose to zero fairly qui kly. we also printed out the square error. Indeed. 23.

We an try to roughly .6) hold exa tly. that the ve tor u does indeed give the exa t dire tion in whi h to move from u ur for whi h the rate of redu tion of the error norm is the largest possible. the error norm is guaranteed to de rease only if the equations su h as (23.ned in Se tion 23.1) does not ne essarily de rease in ea h iteration. It is possible to show.1. This is understandable. however. Thus there exists an su h that the error norm at u ur + u will be stri tly smaller than that at u ur .

and su essively halving it till we .nd this by starting with = 1 (whi h is equivalent to taking the full step. the basi NRM). ie.

23. Display the on. Write the program to solve the box problem. Write the program to solve the hain link problem.nd a point u ur + u where the error norm is lower than at u ur .4 Exer ises 1. 2.

guration of the hain on the s reen after ea h iteration of NRM. 3. Implement the idea of .

For the hain link problem. you will see that this gives smoother movement towards the .nding an using whi h we ensure that the error de reases in every iteration.

nal solution. Something on hemi al equations? . 4.

and Mi rosoft Windows running Cygwin/X.iitb.a . To install. 373 . and follow the instru tions in simple pp/README.txt. We have installed simple pp on Ubuntu. You will need to have the GNU C++ ompiler. whi h is present on all the systems mentioned above.in/~ranade/simple pp.tar untar it. se. download www.Appendix A Installing Simple pp It should be possible to install simple pp on any system whi h has X Windows (X11) installed. Ma OS X.

we have de. the name is a essible only for a part of the program. B. We also dis uss the notion of a global variable.Appendix B S ope and Global Variables When you de lare a name in a program.1 Blo ks So far. We begin by larifying the notion of a blo k. This region of the program where the name is a essible is said to be its s ope. In this hapter we dis uss the general rule for determining the s ope of a name.

and grouped together between a left bra e f and a right bra e g. the notion of a blo k must be modi.ned a blo k to be a group of statements whi h are separated by semi olons. For the purpose of the following dis ussion.

ed slightly in the ase of fun tions and for statements. It is ustomary to onsider the entire de.

Likewise. and not just the body of the for statement.nition of a fun tion to be a blo k (even though the bra es \f\ and \g" only en lose the body of the fun tion). the entire for statement is onsidered to be a blo k. There is one more way in whi h the notion of a blo k must be modi.

ed: the entire .

B. The ase in whi h a variable is de lared several times is more ompli ated.2 S ope First onsider the ase in whi h a name is de lared only on e in the entire program. it is important to note that multiple de larations of the same name are not always allowed. In this ase the rule is simple: the name is a essible in the region of the program text starting at the de laration and going to the end of the innermost blo k ontaining the de laration. Also if a new variable is de lared in the initilization part of the for. First.le is also to be thought as onstituting a blo k. We will all this the global blo k. it is a essible inside the entire for statement. the parameters of the fun tion are a essible throughout the entire body of the fun tion. Note that by our extended notion of a blo k as dis ussed above. This region is the s ope of the variable. De.

374 .ne the parent blo k of a de laration to be the innermost blo k ontaining the de laration.

int k=10. int k=11. { out k << endl. out << k << endl. blo k C begins fourth print statement blo k C ends ERROR The parent of the . 375 Abhiram Ranade. onsider the de larations of k in the following ode fragment. { out << k << endl.1. Do not distribute Then multiple de larations are allowed only so long as ea h de laration has a distin t parent blo k. As an example. } int k=12. out << k << endl. 2011. k = k . NOT ALLOWED. } // // // // // // // // // // // // first de laration first arithmeti statement first print statement blo k B begins se ond print statement se ond de laration third print statement blo k B ends third de laration.

So let us assume that the third de laration is not present. Now there are only two de larations. the parent of the . so this ode is in error.rst and third de larations is the global blo k.

when the orresponding statement is en ountered during exe ution. We will need a rule to determine the s ope of ea h of these de larations (or the asso iated variables). The rule for this is a slight modi. this ode (without the third de laration) is a eptable. and that of the se ond is the blo k named B in the ode. Note that in this ode two distin t variables of the same name k will be reated.rst is the global blo k. in the usual manner. Sin e the parent blo ks are dierent.

We then . in order from top to bottom. Let d . d . dn be de larations of the same name k. ation to the simple rule stated earlier. : : : .

rst .

it will turn out for i < j that si . s . or si will ontain sj . : : : . If some si ontains sj . sj will either be disjoint. Note that ea h si is just a region of the ode. then we will say that di is being shadowed by dj in the region sj .nd the s opes s . sn of ea h of these de larations as per the simple rule. We an now de. Be ause of the distin t parent rule above.

The s ope an also be de. from whi h we subtra t the regions in whi h di is shadowed by another de laration.ne the a tual s ope of a de laration di: it is the region si.

It will be said to be in the s ope of a de laration di if i is largest su h that the simple s ope si de. Consider a statement S in the ode.ned dierently as follows.

our .ned above ontains S . Going ba k to our example.

ex ept for the third print statement. Based on the dis ussion above. the de laration in whose s ope that o urren e is. d .rst and se ond de larations now be ome d . The s ope of d is just the third print statement. we an asso iate a de laration with every o urren e of a name. in the third print statement d shadows d . Thus the . Now we know how the ode fragment will exe ute.e. Then we an determine what value the name represents. The s ope of d is the entire ode fragment. or what is to be updated. i.

rst arithmeti statement is in the s ope of the .

This will ause the value of the variable to hange to 9 from 10.rst de laration. The . so the variable asso iated with this de laration will be used.

rst print statement is also in the s ope of the same de laration. The se ond print statement is also in the s ope of the . Thus this will ause the value 9 to be printed.

1 1 2 2 1 1 2 1 2 2 . so this will again ause the value 9 to be printed.rst de laration.

Do not distribute 376 The third print statement. and hen e the value 11 will be printed. and we de ided that we will remove it from the ode. however. The fourth print statement is in the s ope of the . 2011. Remember that the third de laration is illegal. is in the s ope of the se ond de laration. Abhiram Ranade.

rst de laration. so the value 9 will be printed again. I hope you dont .

If you want a new variable inside a blo k. A variable is reated when the statement whi h de. B. Indeed. you just go ahead and de lare it without worrying whether it interferes with some variable de lared outside. your de laration will shadow the variable within the blo k and not interfere with it outside the blo k. the s ope rules are expe ted to be onvenient.nd these rules too onfusing. Just in ase the same name was used earlier.3 Creation and destru tion of variables In C++ it helps to be lear about when variables are reated and when they get destroyed.

nes it is exe uted. It gets destroyed when ontrol .

nishes exe uting the last statement in the innermost blo k ontaining the de.

The rule is slightly tri ky for variables de lared in loops. At the time of the reation of the variable. then it will get destroyed after ea h iteration. In this ase nothing happens to the variables. They will be available for use when ontrol returns from the alled fun tion. say for exe uting a fun tion all. the onstru tor for the variable is alled.nition and exits this blo k. At the time of destru tion. Note that ontrol may leave this blo k temporarily. and be reated again when the ontrol enters the loop body for another iteration. Similar is the ase for fun tions: the lo al variables de. If a variable is de lared in the body of the loop. the destru tor for the variable gets alled.

e.ned in a fun tion get reated when ontrol rea hes the orresponding statement and destroyed when ontrol leaves the fun tion. If you want the variables to retain their values from one iteration to the next. or from one all to the other. pre. then you an de lare them to be stati . i.

x this keyword in the de.

If the de.nition.

then the initialization will happen only on the .nition in ludes initialization.

rst all or only on the .

Variables de.rst loop iteration.

6) however behave slightly dierently. These variables are reated before the .ned in the initialization part of a for statement (Se tion 6.

in the global blo k. B.4 Global variables It is possible to de lare variables outside of all fun tions (in luding the main program). provided the de laration appears above the respe tive fun tion de. the variable thus de lared will be visible in all the fun tions (unless it is shadowed). In that ase.rst iteration exe utes. and destroyed only after the last iteration exe utes. The notion of stati members in lasses should not be onfused with the use of the keyword here.

nition. and the fun tion de. If there are fun tions.

Variables de lared outside the main program are alled global variables. then the variable is visible in the fun tions as well (unless it is shadowed). .nitions appear below the de laration of the variable.

but indeed it is fraught with danger. This way of using global variables may appear onvenient. It is a tually even more ompli ated { having noted that f refers to a global variable ghi. passing them as arguments to every fun tion might make the ode too verbose. we then need to sear h the ode to see whi h is the last statement to set ghi. If f does refer to global variables. Do not distribute 377 Global variables an serve as a means of ex hanging information between fun tions. This is be ause global variables make it harder to reason about ode. Abhiram Ranade.def). whi h the main program ould then read. then we need to look at the ode to de ide what really ae ts the exe ution of f. the fun tion ould simply write the value into a global variable. 2011. the main program (or any fun tion) ould write data into a global variable. Indeed. Suppose you see a statement: pqr = f(ab . and then all another fun tion. there may be some variables in your program that may somehow be very important and hen e needed in most fun tions. that ee t only depends upon the variables ab and def. Similarly. So the general onsensus is: avoid the use of global variables as mu h as possible. In su h ases it is a eptable to make these variables global. All this is avoided for pure fun tions. and further. whi h an read the global variable and get the data. However. If we know that f does not a ess global variables in anyway (and su h fun tions are often alled pure fun tions) then we know that the f an ae t only the variable pqr. instead of returning a value. .

and provide a onvenient interfa e whi h is generally adequate. The simplest way to use heap memory is to use STL lasses su h as ve tors. maps. if you need to manage the memory yourself. However. strings.Appendix C Managing Heap Memory In Se tion 16. We mentioned that managing heap memory is tri ky.1 we dis ussed heap memory. queues. you need to . These obje ts hide the memory management from the user.

Say we have a large tree T. and potentially save the time required to opy.4 we gave a solution in whi h we ensured that ea h allo ated obje t is pointed to by exa tly one pointer. the onstraint that ea h obje t be pointed to by at most one pointer is not always eÆ ient or onvenient. However. Then it is natural to share the subtree: we should make the appropriate pointer in D point to L rather than needing to make another opy of L to use as part of D.4). This is in fa t the memory management idea used in STL. v being the left and right subtrees. we an tell fairly easily when the allo ated obje t is no longer needed and an be returned to the heap (Se tion 16. spe i. u. A similar example a tually arises in a program for omputing the symboli derivative of an expression. v will appear as subtrees in the formula for the derivative. Suppose that we wish to onstru t another tree D whi h also ontains L.gure out what kind of sharing you want to allow. Consider the rule for dierentiating produ ts: d(uv ) = v du + u dv dx dx dx When we represent symboli expressions as trees (Se tions 17. Let L be a subtree in it.1. In Se tion 16.1). As a result. This will require less memory. but it exe utes behind the s enes.2 and 20. and learly. the produ e uv will be represented by a tree with u.

whi h we might still need. (a) and (b). So it would be natural to ask: an these two trees. be ause that memory might be holding parts of the derivative. the tree for the original expression and the tree for the derivative. If we de ide we dont need the tree denoting the original expression any longer. we annot free the memory used by it. share subtrees. see Figure C. as shown in Figure C. One way to solve this problem is to use referen e ounting 378 .1. ally the left subtree of the right subtree and the left subtree of the left subtree.1( )? The diÆ ulty in sharing resour es is that it is harder to tell when a resour e is not needed.

1: A fun tion and its derivative dv/dx . Do not distribute + * * u * v v du/dx (a) u*v u dv/dx (b) d(u*v)/dx T + D * * u * v du/dx (c) Desired sharing of subtrees Figure C. 2011. 379 Abhiram Ranade.

but we . indi ating how useful that obje t is. Ensuring that the referen e ount is orre tly maintained is tri ky. in this ase ea h node of the tree. Do not distribute 380 C.1 Referen e Counting The basi idea is to asso iate a referen e ount with ea h obje t. The referen e ount of an obje t is simply the number of pointers pointing to that obje t. 2011. Abhiram Ranade.

we want one to be added to its referen e ount. and so we return the memory of X to the heap. For simpli ity we will assume that T is indeed in the a tivation re ord. In this ase we know that the pointer to Y out of X will no longer be of use. Now suppose we write T=NULL. This would make the root of the original expression lose the only pointer it had. Coming ba k to our derivative example. Suppose we did reate the derivative tree su h that it shares nodes with the original produ t tree.rst des ribe what we would like to happen abstra tly. If the referen e ount of Y thus drops to zero. in luding the root is pointed to by 1 pointer. we an return Y also ba k to the heap. If we add a new pointer to point to an obje t. Then every node. In this pi ture. So we would de rement the referen e ount of the root. the roots of the subtrees u. v have 2 pointers oming in. Hen e after reation we would like the roots of these two nodes to have referen e ounts of 2 ea h. and so on. We would . suppose initially we only have the produ t tree. Suppose the tree is pointed to by a variable T. Suppose next we reate the derivative. we de ide that X is no longer useful. as in Figure C. When the ount of an obje t X drops to zero. If we remove a pointer. Hen e at this point we want the referen e ounts of all nodes to be 1. then we want one subtra ted. So the referen e ount of Y should get de remented. Note that we do not asso iate referen e ounts with variables su h as T if they are in an a tivation re ord rather than in the heap. but its root is pointed to by a variable D in the a tivation re ord. Say the nodes of the derivative tree are all on the heap.1( ). Note that X might itself be pointing to an obje t Y.

However. and we have listed out the onditions under whi h this must be in remented or de remented.nd that the root of the original expression has referen e ount 0. These pointers are also a part of C++11. So we an release the memory of the root ba k to the heap. C. its use will also be umbersome.2 The template lass shared ptr This lass provides a standard solution for referen e ounting. It is not too diÆ ult to implement referen e ounting manually. Thus we would like the referen e ounts of the obje ts they point to to be de remented. If after this we set D=NULL then if our referen e ounting me hanism is working all referen e ounts will be ome 0 and everything would be returned to the heap. This lass and the lass weak ptr are known as smart pointers and are available in the Boost Smart Ptr library available from www. the ode is umbersome. v would both be ome 1. This would ause the pointers out of the root (of the original expression) to be ome useless.org. To ea h node we add a referen e ount data member. Thus at this point the referen e ounts of the trees of u.boost. and unless it is designed well. Sin e our . and an be a essed through the GNU C++ ompiler g++ by supplying the option -std=gnu++0x.

the option an also be supplied to s++ to get the fun tionality. 2011. In addition. in your programs you need to in lude the header . Do not distribute 381 ompiler ommand s++ really alls g++. Abhiram Ranade.

Ea h shared pointer has a member fun tion use ount whi h returns the referen e ount of what the shared pointer points to. we de.le <memory>. Note that in the ontext of shared pointers. Thus in many ways a shared ptr is like an ordinary pointer. and an be used almost as onveniently. and of ourse other data needed to manipulate referen e ounts. The dereferen ing and assignment (and other) operators are overloaded for shared ptrs so that they refer to the real pointer ontained inside and also do the bookkeeping needed for referen e ounting. A shared ptr is really a small stru ture that ontains the real pointer.

just rely on the guarantee provided to you.ne the referen e ount of an obje t to be the number of shared pointers pointing to it. You need not on ern yourself with exa tly where the referen e ount is stored.2.1 Syntheti example Figure C. and the output produ ed when the program is run. C.2(a) shows an example of use of shared pointers. The .

the onstru tor of A prints the address of the instan e. After this we print the referen e ounts. Sin e s1 was earlier pointing to 0x804 008. This indeed happens. as shown by the statement printed by the destru tor. s2. This has the ee t that now s1->aptr points to whatever s2 was pointing. This should ause this obje t to be deleted and returned to the heap. These indeed ome out as 0 1. At the end of this group we print the referen e ounts of s1 and s2 only. As you an see s1 points to 0x804 008. and the referen e ounts 1 1 1 are printed for them. the destru tor prints a message saying this. whi h is orre t be ause s1 is NULL and s2 indeed points to 0x804 008. However. Ea h obje t A ontains a shared ptr to another A obje t. Now the three pointers s1. In the se ond group of statements we set s2 to point to a new instan e on the heap. In our exe ution these happened to be respe tively 0x804 008 and 0x804 030. The last print statement indi ates that 0x804 008 also gets deleted. s1->aptr are pointing to unique obje ts. its referen e ount whi h was 1 should drop to 0. In the third group we set s1=NULL. Provided a shared pointer is non NULL. This also happens.rst group of statements reates and initializes two shared pointers s1. s2 to two instan es of A allo ated on the heap. The last statement of the group sets s1->aptr to s2. and is the only one to point to it. When ea h instan e is reated. and if it de rements to 0 to delete that obje t as well. and those of the other two are both 2. a delete on a shared pointer auses the referen e ount of the pointed obje t to de rement. This indeed happens. delete ommands are issued on all lo al variables of the urrent a tivation frame. s2. and nothing else points to it. Thus a delete ommand is issued on s1. so we should expe t its referen e ount to drop by 1. Thus the referen e ount of s1 is 1. Note that s2 was earlier pointing to 0x804 030. and that should get destroyed. This happens be ause when the program exits the s ope. This is . s2 as well as s1->aptr point to the same instan e 0x804 030. Note further that when 0x804 008 is returned. sin e s1->aptr is now invalid. the ontained pointer s1->aptr is no longer valid. Thus the referen e ount of the obje t 0x804 030 pointed to by it should also be ome 0. The reation auses its address 0x804 058 to be printed.

e. Repla e every pointer whi h an potentially point to heap allo ated memory with a shared ptr. 2. Initialize/assign to shared ptr only by a new obje t. For example. use ordinary pointers and allo ate memory but do not worry about returning it. Do not distribute 382 exa tly what happens! C. 2011.. Note that as in the pre eding program. it works quite well for the derivative . you annot write shared ptr<A> s1 = new A. This strategy works well sometimes.2. First write the program without worrying about memory management. i. or by the value of another shared ptr or by NULL. Abhiram Ranade. 3.2 General strategy The pre eding dis ussion might suggest the following strategy for managing memory using shared ptr: 1. but you must expli itly onvert the pointer to a shared ptr.

We will see this in Se tion C. for several reasons. One possibility is that you may have pointers for whi h rule 3 above annot be applied.3. In this ase you will need to reorganize your program. We dis uss this in Se tion C.2. then you will have memory leaks even with shared ptrs.3 Shared pointer in derivative .nding program. However. any implementation of referen e ounting (in luding that provided by shared ptr) has one fundamental limitation: if your pointers form y les. be ause originally they were being used to hold new addresses as well as addresses of variables in a tivation frames. This strategy may not work. C.2.2.4.

nding We .

Then we have a str fun tion whi h onverts the expression represented by the subtree underneath the node into a string. This uses the de.rst develop the ode whi h does not worry about returning dynami memory. Then we have the onstru tor for non-leaf nodes. First we have a onstru tor for onstru ting terminal or literal nodes.1. For this we use the representation for trees developed in Se tion 17. Prod and Lit that in lude the new operator and thus reate the node on the heap. we have the deriv fun tion.1.3. These are onvenient to use and the main program at the end uses them. These follow along the lines of Se tion 17. Next we have fun tions Sum. Finally.2. The ode is shown in Figure C.2.

the derivative of a produ t is as per the rule dis ussed above. the pointer stru tures reated in this program will not have y les. To this ode we an apply our re ipe for adding in shared ptrs. Repla e every Exp* with shared ptr<Exp>. For this it is better to de. and the derivative of a literal is 1 if and only if the literal is x. Also. So we do the following: 1. it is always used to point to heap allo ated obje ts. We only have one kind of pointer in this ode: Exp*. And as you an see.nition: the derivative of a sum is the sum of the derivatives.

.ne typedef shared ptr<Exp> spE. and then repla e Exp* by spE. .

use_ ount() << " " << s2. 2011.} ~A(){ out << "Deleting A: "<< this << endl. // Group 1 s1->aptr = s2. ---------------------. s2 = shared_ptr<A>(new A). A(){ out << "Creating A: "<< this << endl.use_ ount() << endl << endl. } s1 = NULL. Do not distribute #in lude <simple pp> #in lude <memory> stru t A{ shared_ptr<A> aptr.use_ ount() << " " << s2. out << s1.use_ ount() << endl << endl.use_ ount() << " " << s1->aptr.2: Program to test shared pointers and its output 383 . int main(){ shared_ptr<A> s1(new A).Output produ ed -------------------------Creating A: 0x804 008 Creating A: 0x804 030 1 2 2 Creating A: 0x804 058 1 1 1 Deleting A: 0x804 008 Deleting A: 0x804 030 0 1 Deleting A: 0x804 058 Figure C. s2(new A).use_ ount() << " " << s1->aptr.use_ ount() << endl << endl. // Group 2 out << s1. // Group 3 out << s1. Abhiram Ranade.use_ ount() << " " << s2.} }.

} Exp* deriv(){ if(op == '+') return Sum(lhs->deriv(). string value. Exp* rhs. lhs)). Exp::Prod(Exp::Lit("x"). Exp(string v) : value(v) {lhs=rhs=NULL.} stati Exp* Sum(Exp* l. else return Lit(value == "x" ? "1" : "0"). 2011. op='A'.} stati Exp* Lit(string v){return new Exp(v). op(o) { value="". rhs->deriv()). Exp* r){ return new Exp('+'. Exp* f = e->deriv().} string str(){ if (op == 'A') return value. Exp* r) : lhs(l). har op. out << e->str() << endl. rhs). int main(){ Exp* e = Exp::Sum(Exp::Lit("x").} Exp( har o.3: Mini symboli dierentiation program . Abhiram Ranade. else return "(" + lhs->str() + op + rhs->str() + ")".} stati Exp* Prod(Exp* l. else if(op == '*') return Sum(Prod(lhs->deriv(). } Figure C. Prod(rhs->deriv(). rhs(r). r). Do not distribute 384 #in lude <simple pp> stru t Exp{ Exp* lhs. l. Exp::Lit("x"))). l. out << f->str() << endl. } }. Exp* l. r). Exp* r){ return new Exp('*'.

s1 = NULL. s2->aptr = s1. You should observe that while taking the derivative of a produ t uv the expressions for u and v are not opied. s1->aptr = s2. Che k assignments to Exp* variables. you will merely get: Creating A: 0x804 008 Creating A: 0x804 030 Even when the program . then therefore there should be no problem be ause both are onverted to spE. C. there an be new expressions that were assigned to Exp* variables. s2(new A). Abhiram Ranade. Add ode to the onstru tors to observe when they are alled. However. So they must be shared. So you will have to do this. You an also see that the nodes are destroyed when the program terminates. } At this point s1 If you exe ute this. If other Exp* variables were being assigned. and add destru tors so that you know when they are alled as well.2: int main(){ shared_ptr<A> s1(new A). your program should work. With these two steps. s2 = NULL. Do not distribute 385 2.4 Weak pointers Consider a program fragment that uses the stru t A from Figure C. These now have to be expli itly onverted to spE type.2. So there is no memory leak either. 2011.

auses s1. s2->aptr = s1. But it still has 1 referen e. When we set s2 = NULL. you will not get any deallo ations to happen. as you did in the last line of the output of Figure C.2. the reation of s1. { one referen e to 0x804 030 goes away. But this also has one referen e. and s2. Now onsider what happens when we set s1 = NULL. and hen e no delete happens. the pointer inside the . { one referen e to 0x804 008 goes away. the instru tion s1->aptr = s2.s2 aused the messages about reating A to be printed. the obje ts at 0x804 008 and 0x804 030 ontinue to have referen e ount 1. Thus the referen e ounts of all 4 shared pointers are 2. Let us tra e the exe ution to see why.s2->aptr to point to 0x804 008. After that. Thus even after we set s1.s1->aptr to point to 0x804 030. Clearly. s2 to NULL.nishes. next.

C. A weak ptr is a pointer whi h does not in rement the referen e ount. However. But our program annot a ess these obje ts.5 Solution idea This problem an only be solved using so alled the lass weak ptr in onjun tion with shared ptr.2. and they havent been returned to a heap: so we have a memory leak.rst ontributes the ount to the other and vi e versa. if the obje t pointed to . The basi idea is to break every pointer y le by putting one weak ptr in it.

Abhiram Ranade. you an . 2011. then the weak pointer be omes NULL. So whenever you wish to traverse a weak pointer W. Do not distribute 386 by the weak pointer is deleted.

then you might need to lo k the pointer . If you are working in a setting in whi h there are multiple threads.rst he k if *W is not NULL and only then traverse.

3 Con luding remarks Managing heap memory in C++ is an evolving . C.rst.

There is work on so alled garbage olle tion strategies. but that is beyond the s ope of this book. If for some reason you need to go beyond that. your needs will probably be met by the lasses in STL.eld. ideas su h as shared ptr (and also weak ptr if ne essary) will likely be adequate. As a novi e programmer. .

Appendix D Libraries The term library is used to refer to a single .

Suppose you have onstru ted obje t modules g d.o. l m.le whi h olle ts together several obje t modules. Then you an put them into a single library .o.

a for library (ar hive) . and it is ustomary use the suÆx .le. this an be done using the program ar. On unix.

o Here the string r s indi ates some options that need to be spe i.a g d.o l m.a. and so you might hoose to all your library g dl m. This an be done by exe uting ar r s g dl m.les.

When ompiling. whi h we will not dis uss here.a to be reated. This ommand will ause g dl m.ed. you an mention the library .

le on the ommand line. pre.

In fa t you ould send the . modules from it will get linked as needed.xing it with a -L.

along with an header .le to your friends who wish to use your g d and l m fun tions.

h. say g dl m. whi h ontains the de larations of g d and l m (but not the de.le.

be ause you need not send them the orresponding . Note that your friends will not be able to easily know how your fun tions work.nitions). pp . This is the preferred me hanism for sharing ode.

They are in libraries. whi h s++ supplies when needed! Commands su h as sqrt are ontained in the math library that is supplied as a part of C++. Of ourse. Our ompiler s++ automati ally in ludes the orresponding library while it ompiles your programs. These prototypes are present in a .les. D.0. this is not the entire story { you need to have the prototype for sqrt and other fun tions at the beginning of your program.1 Linking built-in fun tions You an now guess how built-in fun tions su h as sqrt or are linked to your program.

le alled math. whi h you an insert into your program by putting the following line at the beginning of your program: #in lude < math> Our ompiler knows where to .h.

nd this .

But did you remember to in lude this .le and pla es it in your program.

le? You might remember that you did put in a similar line in your .

h> 387 .le: #in lude <graphi sim.

2011. Do not distribute 388 Be ause of this the . Abhiram Ranade.

le graphi sim.h is pi ked up from some pla e known to s++ and is pla ed in your .

This .le in pla e of this line.

le ontains the line #in lude < math.h> whi h auses the .

le math.h to be in luded! .

So assume now that the number to be represented is non-zero. We . then it is represented by setting all 32 bits to 0. if the number to be represented is 0.Appendix E IEEE oating point standard First.

rst write the number as 2e. e are respe tively alled the signi. The numbers .

the signi. and and the exponent. Here.

Further. If this ondition is satis. We only retain 23 bits after the de imal point (whi h we should really all the binary point). it is expe ted that the exponent must be in the range -126 and 127. This will of ourse entail some ina ura y. and must be a binary fra tion between 1 and 2.

e + 127 Bits after binary point in 1 if negative Noti e that if 126 e 127. This is a eptable be ause the integer part is always 1 we are ignoring the single bit in before the binary point If the exponent is larger. Thus bits 23-30 are enough to hold the value e + 127.ed. then 1 e + 127 254. 389 . then the number annot be represented .6. then the number is represented as follows. Bit 31 Bits 23-30 Bits 0-22 0 if positive. and not its integer part. 1 1 But also see Se tion 13. Noti e further that we are only storing the bits in the fra tional part of .

Appendix F Reserved words in C++ The following words annot be used as identi.

ers. 390 .

Appendix G Mis ellaneous operators 391 .