LECTURE 14: Pointers (Reference: “Pointers and Memory” handouts,
available from the course web page)
Definition: Pointer is a variable that stores an address of another
variable
Therefore,
pointer is just another variable type!!
The
statement:
int num;
declares
integer variable num and reserves space in memory to store its value. Computer also records the address of the reserved memory
location.
num:
|
address
of num |
value
of num |
The
statement:
int *nump;
declares nump, a pointer to integer, and reserves space in memory
to store its value. The value of nump is address of an integer variable to which nump points to. Computer also records the address of the memory location that
stores value of nump.
nump:
|
address
of nump |
value
of nump |
Example 1:
int num; // value of num is some junk value
int *nump; // nump is
pointer
// value of nump is some junk address
nump = # // value of nump
is address of num variable
*nump = 42; // value of variable where nump points to becomes 42
//
because nump points to num, value of num becomes 42!!
Example 2:
int a = 1; // a is declared as integer and its value is
set to 1
int b = 2, c = 3;
int *p, *q; // p and q are declared as pointers to integers
and
//
their values are some junk addresses
p = &a; //
value of p is is address of a
q = &b; //
value of q is address of b
c = *p; //
value of c is the value of variable to which p points to
//
since p points to a, c = 1
p = q; //
value of p equals to value of q, which is address of b
//
so, p becomes pointer to b too
*p = 13; //
13 is assigned to variable pointed to by p, which is b
//
so, b = 13
Example 3:
int *p; // pointer to integer p is created, its value is some junk
address
*p = 42; //
value 42 is saved at the junk address pointed to by b
// this is very dangerous mistake since the junk address can
// hold some very important
data which will be corrupted by this
Using Pointers as Function Arguments
Similarly to basic variable types (int, double, char), pointers can also be used as function arguments. Use of pointers as function arguments opens new possibilities, such as writing functions with multiple outputs. Let us first illustrate it through the following example.
Program 1. Calculating square of a number (without pointers)
# include <stdio.h>
int x_squared(int x);
void main(void) {
int x = 5, res;
res = x_squared(x);
printf(“%d
squared is %d \n”, x, res);
}
int x_squared(int x) {
int y;
y = x*x;
return(y);
}
Program 2. Calculating square of a number (with pointers)
# include <stdio.h>
void x_squared(int x, int *z);
void main(void) {
int x = 5, res;
x_squared(x, &res); /* observe the difference from program 1 */
printf(“%d
squared is %d \n”, x, res);
}
void x_squared(int x, int *z) {
*z = x*x; /* x*x is stored to where z points to */
}
Some important observations about Program 2:
· x_squared does not use return – this is why it is of void type
· inputs to x_squared are an integer and a pointer to integer
· call to x_squared in main passes value of x and address of res to the function. As a consequence, res variable is visible from x_squared and its value can be changed (by *z = x*x)
Functions with Simple Outputs (Section 6.1 from the textbook)
Motivation: using the return command a function can return only a
single number; using pointers it will become possible for a function with more
than one output.
Example:
Consider function called separate
whose input is a number of type double (e.g. 4.35), and whose output is sign
(e.g. +), whole part (e.g. 4), and fractional part (e.g. 0.35).

Solution: Figure
6.3 (Program That Calls a Function with Output Arguments)
/*
* Demonstrates the use of a function with
input and output parameters.
*/
#include
<stdio.h>
#include
<math.h>
void separate(double num, char *signp, int *wholep, double *fracp);
int
main(void)
{
double value; /* input - number to analyze */
char sn; /* output -
sign of value */
int whl; /* output -
whole number magnitude of value */
double fr; /* output - fractional part of value */
/* Gets data */
printf("Enter a value to analyze> ");
scanf("%lf", &value);
/* Separates data value into three parts */
separate(value,
&sn, &whl, &fr);
/* Prints results */
printf("Parts of %.4f\n
sign: %c\n", value, sn);
printf(" whole number
magnitude: %d\n", whl);
printf(" fractional
part: %.4f\n", fr);
return (0);
}
/*
* Separates a number into three parts: a sign
(+, -, or blank),
* a whole number
magnitude, and a fractional part.
* Pre:
num is defined; signp, wholep,
and fracp contain addresses of memory
* cells where results are to be stored
* Post: function results are stored in cells
pointed to by signp wholep,
and
* fracp
*/
void
separate(double num, /* input
- value to be split */
char *signp, /* output - sign of num */
int *wholep, /* output - whole number magnitude of num */
double *fracp) /* output
- fractional part of num */
{
double
magnitude; /* local variable - magnitude
of num */
/* Determines
sign of num */
if (num < 0)
*signp = '-';
else if (num ==
0)
*signp = ' ';
else
*signp = '+';
/* Finds magnitude of num and separates
it into whole and fractional parts */
magnitude = fabs(num);
*wholep = floor(magnitude);
*fracp = magnitude - *wholep;
}
Example of program execution:
Enter
a value to analyze> 35.817
Parts
of 35.8170
sign: +
whole number
magnitude: 35
fractional part:
0.8170
Explanation of the program:
-
the main function informs separate function of the value of variable value, and addresses of variables sn, whl,
and fr.
-
the separate function creates
memory space to store num variable (of type double), and pointers signp, wholep, and fracp.
-
value of num will equal the value
of value; value of signp will equal the address of sn, value of wholep will equal the address of whl, and value of fracp will equal the address of fr.
-
use of pointers in separate
function allows it a direct access to variables sn, whl,
and fr. This means that separate can directly read and
modify their values. For example,
*signp = ‘-‘;
directly
assigns value of ‘-‘ to sn from the main function.
-
the following
figure illustrates the connection between variables in main and separate functions:

Use of a Single Parameter as Both Input and Output (Section 6.2)
By
use of pointers it is also possible to use the same parameter as both input and
output of a function.
Example:
The
goal is to ask user to enter 3 numbers and order them in the ascending order.
Function order should be used. It swaps the values of two numbers if the first
number is larger than the second.
Solution: Figure
6.6, Program to Sort Three Numbers
/*
* Tests function
order by ordering three numbers
*/
#include
<stdio.h>
void
order(double *smp, double *lgp);
int
main(void)
{
double num1,
num2, num3; /* three numbers to put in order */
/* Gets test data */
printf("Enter three numbers separated by blanks> ");
scanf("%lf%lf%lf", &num1,
&num2, &num3);
/* Orders the three numbers */
order(&num1,
&num2);
order(&num1,
&num3);
order(&num2,
&num3);
/* Displays results */
printf("The numbers in ascending order are: %.2f %.2f
%.2f\n", num1, num2, num3);
return (0);
}
/*
* Arranges arguments in ascending order.
* Pre: smp and lgp are addresses of
defined type double variables
* Post: variable pointed to by smp contains the smaller of the type
* double values; variable pointed to by lgp
contains the larger
*/
void
order(double *smp, double *lgp) /* input/output */
{
double temp;
/* temporary variable to hold one number during swap */
/* Compares values pointed to by smp and lgp and switches if
necessary */
if (*smp > *lgp) {
temp = *smp;
*smp
= *lgp;
*lgp
= temp;
}
}
Example of program execution:
Enter
three numbers separated by blanks> 7.5 9.6 5.5
The numbers in ascending order are: 5.50 7.50 9.60
Explanation of the program:
-
in the main function a user is first asked to enter 3 double numbers
-
then, function order is
called 3 times. In the first call, the values of num1
and num2 are swapped if num1 > num2.
After the three calls to order, the 3 number
entered by the user will be sorted in the ascending order
-
let us suppose we want to solve the swap problem without
using functions. Then, the code would look like this:
if (num1 > num2) {
tmp = num1;
num1 = num2;
num2 = tmp;
}
-
why did we use tmp variable?
-
order function
is given information about the addresses of two variables from main. This gives it opportunity to read and change their
values