an introduction to programming though c++cs101/lectures/lec8.pdfa problem • write a program that...

40
An Introduction to Programming though C++ Abhiram G. Ranade Ch. 9: Functions

Upload: others

Post on 16-Oct-2020

1 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

An Introduction to Programming though C++

Abhiram G. Ranade

Ch. 9: Functions

Page 2: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Can we define new commands?

• We already have many commands, e.g.– sqrt(x) evaluates to the square root of x.– forward(d) moves the turtle forward d pixels.

• Can we define new commands? e.g.– gcd(m,n) should evaluate to the GCD of m,n.– dash(d) should move the turtle forward, but draw

dashes as it moves rather than a continuous line.

• Function: official name for “command”

Page 3: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Outline

• Example of defining and using functions• How to define a function in general• How a function executes• “Contract” view of functions• Passing parameters by reference• Pointers• Functions and graphics objects

Page 4: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

A problem• Write a program that prints the GCD of 36,

24, and of 99, 47.

• Using what you already know:– Make 2 copies of code to find GCD. – Use the first copy to find the GCD of 36, 24. – Use the second copy to find the GCD of 99, 47.

• Duplicating code is not good.– May make mistakes in copying. – What if we need the GCD at 10 places in the

program?– If we need to change later we need to

remember to change in 10 places.– Inelegant: Ideally, you should not have to state

anything more than once.

main_program{ int m=36, n=24; while(m % n != 0){

int r = m%n;m = n;n = r;

} cout << n << endl; m=99; n=47; while(m % n != 0){

int r = m%n;m = n;n = r;

} cout << n << endl;}

Page 5: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Using a function • Code has 2 parts: function definition + main programMain program: • “calls” or “invokes” function.gcd(a,b) : call or invocationgcd(99,47) : another call• Call includes values whose GCD is to be calculated.

– a, b in first call– 99, 47 in second

• Values supplied as part of a call: “arguments to the call”

Function definition:• function name • how it is to be called• what happens when function is executed.

int gcd(int m, int n){ while(m % n != 0){

int r = m%n;m = n;n = r;

} return n;}

main_program{ int a=36,b=24; cout << gcd(a,b) << endl; cout << gcd(99,47)<< endl;}

Page 6: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

General form of function definitions

return-type name-of-function( parameter1-type parameter1-name, parameter2-type parameter2-name, …){ function-body}• return-type : the type of the value returned by the

function, e.g. int. • Some functions may not return anything, discussed

later.• name-of-function: e.g. gcd• parameter : variables that will be used to hold the

values of the arguments to the function. m,n in gcd.• function-body : code that will get executed.

int gcd(int m, int n){ while(m % n != 0){

int r = m%n;m = n;n = r;

} return n;}

main_program{ int a=36,b=24; cout << gcd(a,b) << endl; cout << gcd(99,47)<< endl;}

Page 7: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

How a function executes

• main_program starts execution• Control reaches gcd(a,b)• main_program suspends.• Preparations made to run “subprogram” gcd:• Area allocated in memory where gcd will have

its variables. “activation frame”• Variables corresponding to parameters are

created in activation frame.• Values of arguments are copied from

activation frame of main_program to that of gcd. This is termed “passing arguments by value”.

• a=36, b=24 copied to m, n.

int gcd(int m, int n){ while(m % n != 0){

int r = m%n;m = n;n = r;

} return n;}

main_program{ int a=36,b=24; cout << gcd(a,b) << endl; cout << gcd(99,47)<< endl;}

Page 8: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Execution continued

• Execution of gcd starts.• n = 12 calculated.• Execution ends when “return”

statement is encountered.• Value following the word return, 12, is

copied back to the calling programWill be used in place of the expression gcd(…,…)• Activation frame of function is destroyed,

i.e. memory reserved for it is taken back.• main_program resumes, prints 12, ...

int gcd(int m, int n){ while(m % n != 0){

int r = m%n;m = n;n = r;

} return n;}

main_program{ int a=36,b=24; cout << gcd(a,b) << endl; cout << gcd(99,47)<< endl;}

Page 9: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Remarks

• Set of variables in calling program e.g. main_program is completely disjoint from the set in called function, e.g. gcd.

• Both may contain same name. – Calling program will refer to the variables in its activation frame.– Called program will refer to the variables in its activation frame.

• Arguments to calls/invocations can be expressions– Evaluated, then copied to parameters of called function.

• Function definition must appear before any call to it in the program file.

Page 10: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Remarks

• The body of a function can contain practically anything.– Can create new variables.– Can get input and produce output using cin, cout– Can call other functions, defined earlier.–Main program is also a function, discussed later.– Can use graphics canvas and access turtle created

using turtleSim().– Other graphics objects can also be accessed –

discussed later.

Page 11: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Exercise: Write a program to determine whether a number is even

bool even(int n){ if(n%2 == 0) return true; else return false;}

bool even(int n){ return (n%2 == 0);}

Page 12: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

What we have discussed

• What is a function• How to define a function• How it executes• Next: More examples and how to think of

functions🎻

Page 13: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Exercise: Write function to compute LCM (Least common multiple)

Use the identity LCM(m,n) = m*n/GCD(m,n).

int lcm(int m, int n){ return m*n/gcd(m,n);}

• lcm calls gcd. So gcd definition must appear before lcm.

Page 14: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Program to find LCM using functions gcd, lcm

int gcd(int m, int n){ … return n}int lcm(int m, int n){ return m*n/gcd(m,n);}main_program{ cout << lcm(50,75);}• Functions and main program must appear in the given order.

Page 15: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Execution

int gcd(int m, int n){ … return n}int lcm(int m, int n){ return m*n/gcd(m,n);}main_program{ cout << lcm(50,75);}• main program starts executing• Call lcm(...) reached. Main program

suspends.• Activation frame created for lcm.

• 50, 75 copied to m,n. lcm starts execution.• call to gcd encountered. lcm suspends.• Activation frame created for gcd. • 50, 75 copied to m,n• Execution of gcd starts• gcd computes 25 as result.• Result copied to activation frame of lcm, • Activation frame of gcd destroyed.• lcm continues execution using result. • m*n/gcd(m,n)= 50*75/25 = 150 computed• returned to main_program• Activation frame of lcm destroyed.• main_program resumes and prints 150.

Page 16: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Function to draw dashes while moving

void dash(double d, int n){ repeat(n){

forward(d/2/n); penUp();

forward(d/2/n); penDown();

}return;

}

main_program{turtleSim();repeat(4){dash(100,5);

right(90);}getClick();

}• dash does not return a value, so

its return type is void.• The statement return used in

the body does not have a value after the word return.

Page 17: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Contract view of functions

• Function : piece of code which takes the responsibility of getting something done.

• Specification : what the function is supposed to do: “If the arguments satisfy certain properties, then a certain value will be returned, or a certain action will happen.”

• “certain properties” = “preconditions”• Example: gcd : If positive integers are given as arguments, then

their GCD will be returned.• If preconditions are not satisfied, nothing is promised.• Before you write a function, you should write its specification as a

comment

Page 18: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Contract view of functions (contd.)

• Function = contract between the programmer who wrote the function, and programmers who use it.

• Programmer who uses the function – trusts the function writer to make sure that the execution satisfies the

specification.– does not otherwise care how the function executes.

• Programmer who wrote the function does not care which program uses it.

• Analogous to giving cloth to tailor. – Tailor promises to give you a shirt if the cloth is good.–Wearer does not care how it was stitched.– Tailor does not care who wears the shirt,

Page 19: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Contract view of functions (contd.)

• Postcondition: What is promised about the state of the computer after the function finishes execution.

• Example: After dash finishes its execution we may want it to satisfy the postcondition that the pen is up. – not true for the code given earlier.– Exercise: Modify the code of dash to ensure that the pen is up at

the end.

• Post conditions must also be mentioned in the specification.

• Writing clear specifications is very important.

Page 20: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

What we discussed

• If you are going to execute the same code several times, possibly with different values:– Define a function that executes the code– Call the function with appropriate values.

• Functions can have their own variables which are created in the activation area of the function.– Names can be same in the main program and in the function

• A function is like an independent program except that it gets some values (arguments) from the calling program, and returns results to the calling program.

• Next: Reference parameters🎻

Page 21: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Some shortcomings

Using what we just learned, it is not possible to write functions to do the following:• A function that exchanges the values of two

variables.• A function that produces several values as results:– Function to produce polar coordinates given Cartesian

coordinates.

Page 22: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Exchanging the values of two variables, attempt 1

void exchange(int m, int n){int temp = m;m = n; n = temp;return;

}main_program{

int a=1, b=2;exchange(a,b);cout << a <<‘ ‘<<

b << endl;}

• Does not work. 1, 2 will get printed.

• When exchange is called, 1, 2 are placed into m, n.

• Execution of exchange exchanges values of m,n.

• Change in m,n does not affect the values of a,b of main_program.

Page 23: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Reference parameters

void exchange(int &m, int &n){int temp = m;m = n; n = temp;return;

}main_program{

int a=1, b=2;exchange(a,b);cout << a <<‘ ‘<<

b << endl;}

• & before the name of the parameter:

• Says: “Do not allocate space for this parameter, but instead just use the variable from the calling program.”

• When function changes m,n it is really changing a,b.

• Such parameters are called reference parameters.

• 2 1 will be printed.

Page 24: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Remark

• If a certain parameter is a reference parameter, then the corresponding argument is said to be “passed by reference”.

• Now we can write a program that computes polar coordinates given cartesian coordinates–We use two reference parameters.– Called function stores the polar coordinates in the reference

parameters.– These changes can be seen my the main program.

• There are other ways of returning 2 values – study later.

Page 25: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Cartesian to polar

void CtoP(double x, double y, double &r, double &theta){

r = sqrt(x*x + y*y);theta = atan2(y, x); //arctan

return;}main_program{

double x=1, y=1, r, theta;CtoP(x,y,r,theta);cout << r <<‘ ‘<< theta << endl;

}

• r, theta in CtoP are reference parameters,

• changing them in CtoP changes the value of r, theta in the main program.

• Hence sqrt(2) and pi/4 (45 degrees) will be printed.

Page 26: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Exercises

Write a function which takes a length in inches and returns the length in yards, feet, and inches. Note that 12 inches make a foot, and 3 feet make a yard. As an example: 100 inches = 3 yards, 2 feet, 4 inches. Hint: your function will have 4 parameters, one in which you will pass the given length, and the other 3 in which the function will put the the number of yards, number of feet and number of inches.

Page 27: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

What we discussed

• If we want to return more than one result we can do so by using a reference parameter.

• If we use a reference parameter R in a function, and pass as argument a variable A, then any change that the function makes in R will be seen by the calling program as a change in A.

• Next: Pointers, which perform a similar function.🎻

Page 28: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Pointers

• If the memory of a computer has N bytes, then the bytes are numbered 0..N-1.

• The number of a byte (different from what is stored in the byte) is said to be its address.

• A pointer is a variable that can store addresses. – Sometimes “pointer” might mean address.

• What we accomplished using reference variables can also be accomplished using pointers. – This will be seen soon.

• Pointers will also be useful elsewhere.

Page 29: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

How to find the address of a variable

• The operator & can be used to get the address of a variable. – The same & is used to mark reference parameters; but the meaning will

be clear from the context.

int t;cout << &t << endl;• This prints the address of the variable t, i.e. the address of the

first byte that comprises the variable t. • Customarily, addresses get printed in hexadecimal radix, i.e. they

will consist of a sequence of hexadecimal digits prefixed by “0x”• Note: hexadecimal digits: 0,1,2,3,4,5,6,7,8,9,A,B,C,D,E,F.

Page 30: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Variables that can store addresses

• How to create a variable for storing addresses of variables of type int :

int *v; // read as “int star v”• The * is not to be read as multiplication. – Think of it as (int*) v; where int* means the type: “address of int”.

int p;v = &p; // address of p stored in v• Since p is of type int, &p has type address of int. • Thus, it is OK to store &p in v, which is also of type address of int.cout << v <<‘ ‘<< &p << endl; // both print samev = p; // compile time error: type mismatch

Page 31: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Pointers in general

• In general, to create a variable w to store addresses of variables of type T, write:

T* w;• Assignment statements: types of lhs and rhs must be same– Except when both sides are numeric types; then conversion rules

used.– No conversion rule between pointers of one type and pointers of

other types.– No conversion rule between pointers of one type and values of

any type.

Page 32: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

The dereferencing operator *

• If v contains the address of p, then we can get to p by writing *v.int *v;int p;v = &p;*v = 10; // as good as p = 10.• Think of * as the inverse of &. • &p : the address of the variable p• *v : the variable whose address is in v• int *v; – v is such that *v is an int– v is an address of an int

Page 33: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Pointers in functions

void CtoP(double x, double y, double *pr, double *ptheta){ *pr = sqrt(x*x + y*y); *ptheta = atan2(x,y); return;}main_program{ double r, theta; CtoP(1,1,&r,&theta); cout << r <<‘ ‘ << theta << endl;}

• main_program calls CtoP, supplying &r, &theta as third and fourth arguments.

• This is acceptable because corresponding parameters have type double*.

• The first step of the call copies the addresses of r,theta of the main_program into pr, ptheta of CtoP.

• *pr means the variable whose address is in pr, in other words, the variable r of main_program.

• Thus CtoP changes the variables of main_program.

• Thus r becomes √2 = 1.41 and theta becomes π/4 = 0.79 and are printed.

Page 34: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Remarks

• In variable definitions, * associates to the right. Example:int *v, p;• This means int *v; and int p; i.e. defines a variable v of type int*, and variable p of type int.

• For now, assume that the only operations you can perform on a variable of type T* are– dereference it, – store into it a value &v where v is of type T, – store it into another variable of type T*– pass it to a function as an argument, provided corresponding parameter

is of type T*

Page 35: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Exercise

• Point out the errors in this code.int *p, *q, w;p = w;q = 3;• What is the result of executing the following:int *p, *q, w, x;p = &w;w = 10;q = &x;*q = 20;cout << *p + x <<endl;

Page 36: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

What we discussed

• A pointer is an address or a variable containing an address.• A pointer to a variable can be created in the main program

and dereferenced during a function call.• This way a function can be allowed to modify variables in

the main program, or other functions.• Pointers can do the same thing as references, but the

notation is clumsier.• But pointers can do other things too. (Later)🎻

Page 37: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Functions and graphics objects• You can pass graphics objects to functions.• The parameter must have the same type,

i.e. shape.• If you pass by value, a copy of the variable

is made for use in the called function.– The copy is destroyed when the function returns.

• If you pass by reference of pass a pointer, the function can operate on the original graphics object.

• If you imprint an object in a call, the image will survive after the call finishes.

• Incidentally, you can make a copy of an object even using assignment

Rectangle r(100,100,80,20); Rectangle s=r;

void Rev360(Rectangle &r){  repeat(36){    r.right(10);    r.imprint();    wait(0.01);  }}

main_program{  initCanvas();  Rectangle r(100,100,80,20);  Rev360(r);  getClick();}

Page 38: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Exercise

Write a function which takes a rectangle and coordinates x, y as input and decides whether the point (x,y) lies inside the rectangle.You will need to know the following useful operations that can be performed on any rectangle R.• R.getX() : returns the x coordinate of the rectangle center• R.getY() : returns the y coordinate of the rectangle center• R.getWidth() : returns the width of the rectangle• R.getHeight() : returns the height of the rectangle

Page 39: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Concluding remarks

• If you find that you are performing the same operation at several places in your program, consider making it into a function.

• Function = “packaged software component”.– The user of the function does not need to worry what happens inside the function.– The user only expects the specification of the function to be honoured.

• Arguments can be passed by value: – If corresponding parameter is modified in function, no direct effect in calling program.

• Arguments can be passed by reference: – If corresponding parameter is modified in function, variable in calling program

changes.

• Argument is a pointer to a variable in the calling function:– Code in called function can access variable by dereferencing pointer.

Page 40: An Introduction to Programming though C++cs101/lectures/Lec8.pdfA problem • Write a program that prints the GCD of 36, 24, and of 99, 47. • Using what you already know: – Make

Exercises

• Write a function that draws an n sided regular polygon such that each side has length s, and returns the perimeter (n*s) as the result.

• Write a function that returns the cube root of a number using Newton’s method. Have an additional parameter to the function for specifying the number of iterations you want performed.

• Other exercises at the end of Chapter 9.🎻🎻