Fortran95 Notes

You might also like

Download as pdf or txt
Download as pdf or txt
You are on page 1of 24

FORTRAN 95 • Select: New

an introductory course You should now have a blank white window ready for
entering your program
Chapter 1 Before starting to type in your program it is best to give
Getting started your program a name by saving it. (though at this stage there
is nothing to save)

1.1 Introduction • Select: File SaveAs


• Enter a file name: prog1.f95
Computers are controlled by software (or programs).
Whenever the computer is switched on there is always a You can use any name instead of prog1 for your program
program running. This may only be controlling the display, but the extension .f95 is essential.
waiting for input from the keyboard , the mouse or via a
network, or it may be a more specific piece of software that If you wish to save your program in a different directory
is running such as a spreadsheet, a word processing package then this is possible using the dialogue box.1
or a mail program such as Pegasus.
1.5 Task 1 - program simple
This short course in FORTRAN 95 will give you an
introduction to some of the basic ideas used in most The following simple program illustrates the basic steps
programming languages. In many respects the language we involved in preparing and running a program using Plato
are using is irrelevant, though FORTRAN is more suited for
scientific and numerical computing rather than, say, • As in 1.4 above start a new program and name it
constructing a Web page, where Java might be more task1.f95
appropriate. • Type in the following program:
1.2 Plato
program simple
At City we are using Salford FORTRAN 95. In order to real x
construct a program we need to be able to enter the read(*,*) x
instructions (compose, edit) and then transform them x=x+1
(compile and link) into a form that can be acted upon (run) write(*,*) x
by the computer. The finished program will also need to be end simple
saved for further use. To carry out this process the Salford
company have written an Integrated Development
Environment (IDE) called Plato. Since during the process
NB. Plato will automatically add the bold face to certain
of constructing and running a program you will make many
words. (see 1.6)
mistakes Plato has been designed to help you identify your
errors (debugging).
• The program now needs to be compiled, linked and
run. These three steps can be done with one click of
1.3 Getting started
the [execute] button. This is the fourth button from
Assuming that you are logged in to the City University the right hand side of the button bar and has a single
system you need to locate the Salford software and run black arrow head icon.
Plato. To do this you need to click the following on the • Execute the program.
desktop:
If successful:
• Start
• Programs • You will be presented with a black window
• Programming Languages and a flashing cursor.
• Salford Software • The program is now running and waiting for
• Salford Plato IDE you to input a number
• Type in a number (4 say) and press the enter
This should open the Salford Plato window, you are now key
ready to start a new program or edit one you prepared • Your program should add one to the number
earlier. and then write out the result (5 in this case).
• Press enter to return to your program

1
1.4 Creating a new program The U drive is your own personal space on the City system and
programs saved there will be available the next time you logon. The D
To create a new program: drive is local to your machine and work saved there will be lost when
you logout or at best at the end of the day. You can save programs on
• Select: File (from the top line) the A drive if you insert a floppy disc into your computer

1
• Select [OK ] to get rid of the Build successful but must, if used, be the same as the program name
window or RUN to run your program again used in the first line.

If unsuccessful: 1.7 Task 2 - program compound

• You will get a Build Failed window instead If I invest £a at r% for n years then the amount at the
of the black input window. end of the period, assuming that the interest is compounded
• Click the [Details] button to get information annually is given by : A = a (1 +
r n
) . The task is to
on your error(s) 100
• This will open an Error and Warning write a FORTRAN program to calculate A , given the initial
window sum a, the annual percentage interest rate r and the number
• Click on the first message in the error and of years n.
warning window, this will highlight the
position of your error in the program This We will design the program to:
together with the message should help you • request the input of the three unknowns a, r and n
correct your program • identify on the screen the output of the result
• Correct all errors
• Try to re-execute your program
• Start a new program and name it task2.f95
• Save your program • Type in the following program:

Although Plato should automatically save the program compound


program every time you try to compile a new real a, r, capital
version, just to make sure you should save the
integer n
program using the save button (third from the left
write(*,*) ‘input the initial amount’
on the top button bar).
read(*,*) a
1.6 Details of program simple in task 1 write(*,*) ‘input the interest percentage rate’
read(*,*) r
The program simple in 1.5 consists of six lines each write(*,*) ‘input the number of years’
carrying out a specific task in the order in which they are read(*,*) n
written. The words in bold face (such as real) are reserved capital = a*( (1+r/100)**n)
words and have a special meaning. Plato will change these write(*,*) ‘final amount = ‘, capital
to bold automatically.
end compound
• program: this is optional, its purpose is to enable you
to identify the program. It is followed by a space and a
name which can be any string of letters and numbers
without spaces. • Execute the program as in 1.5 above providing your
own values of a, r and n. I suggest you use simple
• real: this tells the computer that the variable x is to be
values so that you can check that the program is
treated as a real number and stored in a standard
running correctly.
exponential form. (e.g. +2.13 10-2 for 0.0213 ) An
alternative to real is integer where the variable is
stored exactly. There are other differences in
1.8 Details of program compound in task 2
FORTRAN between real and integer that become
important later on.
• real a,r,capital This statement declares three real
• read: this tells the computer to wait until you type in a
variables, a, r and a third variable called capital, each
number at the keyboard. The variable x is then given
being separated by a comma. In general variables can
this value. The (*,*) part of the instruction is used later
be given any name consisting of letters and numbers
to control how and where from the number is to be
starting with a letter. Thus the shortest variable name
read. (it may be from a file on the hard disc)
is a single letter.
• x=x+1 This is not an equation. It has the effect of
adding 1 to the existing value of x. In words ‘x
• write(*,*) ‘input the initial amount’ In order to send
becomes x plus one’ Thus if x has the value 4,
a message to the screen requesting the input of a piece
because you have entered 4 from the keyboard, then
of data, namely the initial amount of the capital, we use
after this statement it has the value 5
the write statement. The character string ‘input the
• write: this tells the computer to write the value of x to initial amount’ is written to the screen without the
the screen. It was this statement that caused 5 to be quote marks. It is the quote marks that identifies it as
displayed on your screen when you ran the program and being a character string and not a variable name or list
input the value 4. of names.
• end: this signals the end of the program, and is
essential. The program name following this is optional • read a After prompting the user with the message to
input the initial amount the program uses the read

2
statement to input its value. The program will wait Write a program to find the least number of one, two, five,
until a value is input at the keyboard. On input the ten, twenty and fifty pence pieces that make up a given
variable a is set equal to this value. number of pence. For example 123p consists of 2 fifty
pence pieces, one twenty pence piece, one two pence piece
• capital = a*( (1+r/100)**n) and one one pence piece. Such a program would be useful
FORTRAN uses: in calculating the amount of change required in a vending
machine.
** for powers
* for multiplication
/ for division We can see how the program will work by looking at how to
+ for addition calculate the number of fifty pence pieces in the above
- for subtraction example of 123p.
Using integer division 123/50 = 2 exactly the number of
Although there are rules for controlling the order in which fifty pence pieces in 123p. The amount remaining, which
expressions are evaluated the use of brackets is still has to be split up is given by 123 - 50*(123/50) = 23
recommended.
We repeat this process next with 20 then 10,5,2 and finally
Since ** is given a higher precedence than * the above 1.
expression for capital could have been written as
a*(1+r/100)**n The bracket will be raised to the power n Complete the following program , save it as task3.f95 ,
before it is multiplied by a. run and test it.

Question In your program remove all the brackets from the Note the inclusion of comment lines which are there solely
expression for capital and run your program with a=1, r=100 to help you follow the program . A comment is preceded by
and n=2. Is the answer what you expect? !

• write(*,*) ‘final amount = ‘ , capital program change


The write statement is used here to output two items, ! n is the amount to be broken into change
the character string ‘final amount = ‘ and the value of ! one, two, five, ten, twenty, fifty are the number
the variable capital; note that the two items are ! of coins of respective denomination in the change
separated in the statement by a comma. integer n, one, two, five, ten, twenty, fifty

1.9 Integer arithmetic ! request input of amount to be changed and write first line of
! final output
If we declare a variable n as being an integer then its value write(*,*) ‘input amount to be changed’
will be stored exactly. The range of values that an integer
can take will depend on the system being used, we need not read(*,*) n
bother with this constraint at the moment. There are two write(*,*) n , ‘ pence breaks down into’
important side effects that we need to be aware of:
! calculate the number of fifty pence pieces
a) The statement n=23.1 will result in n being given the ! and set n equal to the remaining change
value 23. Since n is to be an integer the decimal part fifty=n/50
of the number is truncated. Indeed assignment of n to n=n-fifty*50
any real value or real expression will result in n being
truncated to an integer. Write code for twenty ten five two and one
b) A more surprising result is that obtained with integer
division. If one integer or integer expression is ! output the results
divided by another then the result is truncated. Thus: write(*,*) fifty, ‘ fifty pence pieces ‘
2/3 = 0
7/2 = 3 Write similar code for the others
if n=14 then n/3 = 4
end change
NB 2.0 is treated as a real because of the decimal point,
thus 7/2.0 would be calculated as 3.5

Usually one has to be careful when carrying out a division You should run this program using different amounts and
if integers or integer variables are involved, however this check your results by hand.
apparent shortcoming can be exploited as we see in the next
task. 1.11 Details of program change in task 3

1.10 Task 3 - program change • integer n, one, two, five, ten, twenty, fifty This
declares the seven variables as integers. Note that we
have used words for the variables that relate to their

3
meaning in the program. Doing this makes it easier to
follow the program.

• write(*,*) n , ‘ pence breaks down into’ This


statement writes two items to the screen. The value of
n, which at this stage in the program is equal to the
amount to be split into change, and the character string
‘pence breaks down into’

If n has the value 123 then on execution of this


statement the following is written to the screen:

123 pence breaks down into

• fifty=n/50 This statement is the key statement that


exploits integer division. The result of dividing n by
50 is to calculate how many fifties there are in n, the
remainder being discarded.

To see this suppose that n=123 then 123/50 = 2.46


but the integer division discards the 0.46 leaving
fifty=2.

To calculate the remainder, which we need for the


rest of the program we use the next statement:

• n=n-fifty*50 Using the data from above n=123 and


fifty=2 thus n is reset equal to 123 - 2*50 = 23 Thus
we start the problem again with n=23 and in the next
step, which you should have written, you calculate the
value of twenty. Continue this through ten ,five, and
two to one.

Exercise 1.1

a) Write a program to input a real number x and output


the areas of the square with side x, the circle with
radius x and the equilateral triangle with side x
b) For given integers n and m write a program to calculate
the remainder when n is divided by m. i.e. Your
program should read in values of n and m from the
keyboard and write out the remainder to the screen.
c) The natural exponent e can be defined as the limit of
N
 1
1 +  as N gets larger and larger. Amend your
 N
program compound in (1.7) to calculate this function.
You should allow N to be input by the user. Run your
program with different values of N to obtain an
approximation to e correct to 3 decimal places.

4
Chapter 2 • temp=x Since we are about to swap the values of x
and y , in order to put them in ascending order, we
Control Structures need to save the value of x before we start. This
statement saves the original value of x in temp. ie
temp=4.
2.1 Conditional Branching - if… ..then • x=y The original value of y is now placed in x. ie
x=2. If we hadn’t saved the original value of x it
It is often necessary to decide between two courses of would at this stage be lost.
action. For example if we are about to calculate a/b then we • y=temp The original value of x, which has been stored
should first test to see if b=0. If b=0 then we should not in temp, is now placed in y. ie y=4.
attempt to carry out the division but follow some other
• write(*,*) … … .. Outputs the values of x and y to
course of action.
the screen.
In the following short program, which you should attempt to
run, the if statement is used to sort two numbers into
2.3 Logical Expressions
ascending order.
A logical expression is an expression that has the value
true or false. As in the above example x>y is a logical
Program sort
expression and is true when x=4 and y=2 but is false if x=2
real x,y,temp
and y=4.
write(*,*) ‘ input two numbers’
read(*,*) x,y As you would expect we can also use the following:
order: if (x>y) then x<y x less than y
temp=x x<=y x less than or equal to y
x=y x==y Yes there are two equal signs for x=y as a
y=temp logical expression
end if order x/=y x not equal to y
x>y x greater than y (as in the program above)
write(*,*) ‘in ascending order the two numbers are’,x,y x>=y x greater or equal to y
end sort
The above logical expressions can be combined using one
The syntax of the if statement is: or more of the following:
.or.
[name:] if (logical expression) then .and.
statements .not.
… … … … For example if we wish to execute a piece of code when x is
… … … … larger than y and z then we would use:
end if [name] if ( (x>y) .and. (x>z) ) then
… … … …
The use of square brackets around the initial [ name:] and … … … …
the final [name] indicate that they are optional. 2 They are end if
simply used to make the program more readable.
NB The outer brackets are essential and contain the
logical expression (x>y) .and. (x>z) The brackets in this
2.2 Details of the program in 2.1 expression are not essential but are recommended.
As with arithmetic expressions there are rules for evaluating
• real x,y,temp declares that the three variables x,y and logical expressions but this is best controlled using brackets.
temp are to be treated as real numbers
• write(*,*) ‘ input two numbers’ FORTRAN, like most programming languages, allows us to
read(*,*) x,y These two statements deal with the have variables of type logical. With care these can be
input of the two numbers to be placed in order. The manipulated to great effect, however, in this introduction
first issuing a message to the sceen and the second we will restrict ourselves to the above arithmetic use.
waiting until the user has typed in two numbers
separated by a space. Assume that you have input 4 2
ie x=4 and y=2
• if (x>y) then This tests to see if x is greater than y,
which in this example it is. Thus the next three lines
of code are executed. If x is not greater than y then the
program jumps to the statement after the end if order
statement.

2
[ ] in a syntax context will always be used to indicate that the
contents of the bracket are optional. The brackets do not form part of
the statement!

5
… … … … … … … … … … …
2.4 Task 4 - program quadratic1 - sqrt( ) … … … … … … … … … … …
else [name]
The quadratic ax + bx + c = 0 has two real solutions … … … … … … … … … … …
2
… … … … … … … … … … …
− b ± b 2 − 4ac end if [name]
given by x = provided that a ≠ 0 and
2a
• As before the use of a name is optional.
b 2 ≥ 4 ac .
• You may have as many else if as you wish.
Complete the following program that inputs real values of • The final else is also optional, but is usually present to
a, b and c and outputs the two real solutions. The program deal with the case when all the other logical
expressions have been false. (ie when all else fails)
should test that a ≠ 0 and b 2 ≥ 4 ac before attempting to
use the formulae.*
2.6 Task 5 - program quadratic2
The program denotes the two real solutions as x1 and x2.
Rewrite quadratic1 to deal with any of the above cases:
program quadratic1
real a,b,c,x1,x2 program quadratic2
write(*,*) ‘input a ,b and c ‘ real a,b,c,x1,x2
read(*,*) a,b,c write(*,*) ‘input a ,b and c ‘
read(*,*) a,b,c
test: if ( logical expression) then
x1= … … … . if ( (a==0) .and. (b==0) .and. (c==0) ) then
x2= … … … .. write(*,*) ‘the quadratic is satisfied for all x’
write(*,*) … … … .. else if ( (a==0) .and. (b==0) ) then
end if test write(*,*) ‘the quadratic has no solutions’
end quadratic1 else if (a==0) then
x1=-c/b
Run your program with the following sets of data: write(*,*) ‘equation is linear with x = ‘,x1
else if (
a) a=1,b=3,c=2
b) a=1,b=2,c=1 … … … … … … … ..complete the program… … … … … ..
c) a=1,b=1,c=1
d) a=0,b=2,c=4

You will observe that the program is less than helpful for c) Test the program with a range of data that tests each part of
and d). To write a complete program to solve the quadratic the program.
we need to introduce a more complete form of the
conditional branching statement.
2.7 Task 6 - decode

This is the reverse of a programming exercise, the object of


2.5 Conditional Branching the task is for you to read the program and then draw the
graph of the function that is defined by the code.
In the quadratic example if a=0 then we can still solve the
c
problem, indeed x = − provided b ≠ 0 . If both a and b Given the following program describe its action and sketch
b the function that is being defined. Pay particular attention to
are zero then the quadratic is satisfied only if c happens to the case n=m.
also be zero. Furthermore if a ≠ 0 and b = 4 ac then the
2
Your description should also include details of the input
quadratic will only have one solution. Finally if a ≠ 0 and
required and the output observed on the screen.
b 2 < 4 ac then there are no real solutions. For the program
to be able to deal with all these possibilities in an efficient If you wish you can type in and run the program though this
way we introduce a more elaborate form of conditional is not necessary for the exercise.
branching.
program decode
real x,y,n,m,temp
[name:] if (logical expression) then write(*,*) ‘input two numbers, n and m’
… … … … … … … … … … . read(*,*) n ,m
… … … … … … … … … … . swap: if (n<m) then
else if (logical expression) then [name] temp=m
m=n
*
In FORTRAN the square root function is n=temp
sqrt(real expression)

6
end if swap must respond by writing to the screen a message saying
write(*,*) ‘input the value of x ‘ input must be positive, please try again.
read(*,*) x
To achieve this it is necessary to continue to execute a read
function: if (x<=m) then statement and test the input until the input is greater than
y=x**2 zero.
else if ( (x>m) .and. (x<n) ) then
y=1 FORTRAN introduces the unbounded do loop as follows:
else
y=x+1 [name:] do
end if function … … … …
write(*,*) ‘at x = ‘,x, ‘the function = ‘,y … … … …
end do [name]
end decode
This piece of code would execute itself for ever if we didn’t
introduce the exit statement.
2.8 Simple if
The exit statement makes the program jump down to the
If we only need to execute one statemet depending on statement after the next end do. i.e. the current do loop is
whether or not a single logical expression is true the we can terminated.
use the simplified version of the above if statements.

if (logical expression) single statement Consider the following program:

Example 1 program nice_input


When about to calculate the square root of a real x
number we may wish to stop the program if the number is
negative. We could use the lines write(*,*) ‘input a positive number’

if (x<0) stop do
y=sqrt(x) read(*,*) x
if (x>0) exit
These two lines of code will set y = x if x ≥ 0 but stop write(*,*) ‘input must be positive, please try again’
end do
the program if x<0. end
The FORTRAN instruction stop stops the program
Task 7
completely and can be followed by a message which is
output to the screen. Thus a more informative piece of code
Enter the above program and run to satisfy yourself that it
would have been:
does only take in positive values. Try inputting a character
if (x<0) stop ‘negative square root encountered’ rather than a number.
y=sqrt(x)
Task 8 - triangle - :: - &
Example 2
1
In a program to calculate y = if x ≠ 0 and set In triangle ABC, the angles A and C, and the side AC are
x known. Calculate angle B and the other two sides. This can
y = 1 if x=0 we could use the following be done using the sine rule and the fact that the angle sum
y=1 of a triangle is 180 degrees. The task is to write a program
if (x/=0) y=1/x which will take as input two values for the angles,
measured in degrees and a value for the side. Clearly all
instead of an if then else structure. three quantities must be positive and the sum of the two
angle must be less than 180. Thus the program must test
The key point with the simple if structure is that it can only that the input satisfies these criteria before it starts to
be used when there is only one statement to be executed. calculate the third angle and the other two sides. Your task
is to complete the following program.

2.9 do loop - unbounded do - exit NB The FORTRAN function sin(x) requires x to be in


radians thus to calculate the sine of A degrees we need to
Consider the following problem: write sin(A*pi/180) where we have set pi equal to the value
of π
Write a program to input a real positive number x. If the
user inputs a negative or zero number then the program Program triangle

7
!declare and initialize the variable pi Complete the following program and hence run with
real :: pi=3.1415 suitable values of N to check that your program is correct.

! declare the angles and sides of the triangle Program sum


real A,B,C,AB,AC,BC integer :: I ,N,sum=0,formula

! issue initial invitation for input and start do loop write code to input a positive value of N - see task 7
write(*,*) ‘input two angles A and B &
&and side AB of triangle ABC’ do I=1,N
do sum = sum + I*I
read(*,*) A,B,AB end do
if (… … … … … … … ) exit
write(*,*) ‘all input must be positive and angle sum<180’ write code to evaluate the summation using the formula
end do formula =

! Calculate the third angle and other two sides write code to output the value of sum and the value of
C = formula, identifying which is which. They should be the
AC = same of course!
BC =
end sum
! output results
write(*,*) … … … … … … … … … … The do loop first makes the trip with I =1 then with I=2 etc
up to I= N. The order in which the above process is
end triangle carried out is:

a) We can simultaneously declare and initialize variables 1) first set I=1


as we have for the variable pi above. In general we can 2) if I ≤ N then execute the code down to the end do
declare some and declare and initialize others in one 3) if I >N then jump to the next statement after the end
statement. do.
The line: 4) increase I by one
real :: x,y,z=1,w,v=1.2 5) repeat the process from (2) with the new value of I .

declares the variables x, y, z, w and v as real and initializes The general form of the do loop is given by:
z=1 and v=1.2 The other variable have no defined value at
this stage though most systems will give them the value [name::]do variable = expression1, expression2
zero. [,expression3]
… … … … … … … … … … … … … … … …
b) The & sign is used to extend the line - the lines are … … … … … … … … … … … … … … … …
joined at the & signs but the signs themselves are not end do [name]
printed out.
As usual we can add an optional name to the process.
2.10 do loop - bounded do
variable is an integer and expression1 and expression2 are
One of the strengths of the computer is the ability to repeat integer expressions. In the above, expression1 is just the
operations over and over again. In the case of the number 1 and expression2 is the trivial expression N. The
unbounded do loop we need an exit statement to stop the optional integer expression3 allows us to increment the do
repetition. We now look at a do loop that only executes a loop variable by increments other than 1.
given number of times. If expression3 is negative then the variable will be
decremented and the loop executed until the variable is less
than expression2
Task 9 - Summation Σ
Consider the following :
Consider the following simple problem:
sum=0
i= N

∑i 2
do I = 2*N*N, N**3, 4
Evaluate where N is provided by the user. sum=sum+I*I
i =1 end do
Since we know a closed form formula for this expression:
i= N
N ( N + 1)(2 N + 1)
∑i
If initially N=3 then the first line of the do loop reads
2
= we can check the program. do I=18, 27, 4 and will produce
i =1 6
sum = 18 + 22 + 26 = 1484
2 2 2

8
interest charged for that year is r Yn . Thus at the start of
Since initially I starts at 18 and is incremented by 4, when it
the (n+1)th year the total owing is Yn (1+ r ) − a since we
reaches 30 it fails to be less than the upper limit 27 and thus
the process is terminated and the program continues on past have repaid £a during the nth year. Mathematically we can
the end do. At this point sum has reached the above value. write:

NB If initially N=1 then the code in the do loop is never Yn + 1 = (1 + r )Yn − a


executed since the first line of the do loop now reads: This is a simple recurrence relation which has solution
do I =2, 1, 4 The initial value of I is 2, which is greater
than the upper limit 1 hence the process jumps to the a a
statement after the end do. Such a do loop is referred to as Yn = (Y1 − ) (1 + r ) n − 1 +
r r
a Zero Trip do loop
To calculate the annual repayments we set n=N+1 and
.
Task 10 * - sum up or down
YN + 1 = 0 . This gives :
r (1 + r ) N
In task 9 we did not allow N to be zero or negative. a= Y1
However if N is zero or negative we can interpret the (1 + r ) N − 1
i= N i =1
summation ∑i =1
i 2 to be ∑i
i= N
2
. Thus if N = − 2 the
We are now in a position to write a program which for a
summation is : given loan, interest rate and period of repayment will
calculate the monthly repayments and print out the amount
( − 2) 2 + ( − 1) 2 + (0) 2 + (1) 2 owing at the start of each year. We can either use the
recurrence relation or the solution to calculate Yn , I will use
which can be rewritten as : (1) 2 + (0) 2 + ( − 1) 2 + ( − 2) 2 the recurrence relation as it is a more flexible approach if
the interest rate is variable.
This is now a summation with increment -1 rather than 1.
Thus irrespective of the sign of N we can carry out the Complete the following program
summation using the same do loop do I =1, N , M where we
set M=1 if N >0 and set M=-1 otherwise. program repay_loan
real r, Y1,Y,a
Rewrite program sum in task 9 to allow for any integer integer I,N
value of N by:
• declaring a new integer M ! Y1 is the initial investment and Y the variable Yn above
• relaxing the input to allow for any integer N
! r is the interest rate and a the annual repayment.
• setting M=1 if N>0 and -1 otherwise
! N is the length (term) of the loan in years
• rewriting the do loop as do I =1, N , M
continued… … .
• removing reference to the formula method which is
only correct for positive N, or if you wish retain it for
write code to input positive values for the interest rate r,
N>0 only.
initial amount Y1 and term of loan N
I suggest that you invite the user to input the rate as a
percentage and then convert to a decimal with r=r/100

Task 11 - Loan Repayment Problem - iteration


! convert r to decimal
r=r/100
Consider taking out a loan at a fixed interest rate r over a
period of N years. Repayments are to be made in equal
! calculate a/12 and write monthly repayment to screen
monthly installments but the interest is calculated and
a = use the above formula for a
compounded annually.
write(*,*)… … … .
Let Yn stand of the amount of the loan outstanding at the !Calculate amounts owing and write results to screen
beginning of the n th year. Thus Y1 is the initial amount of do I =1,N+1
the loan and YN + 1 = 0 if the loan is to be paid off in N write(*,*)… … output Y1 and N with suitable message
Y=(1+r)*Y1-a
years. ! reset Y1
Y1=Y
Let a be the annual repayment (monthly repayment = a/12) end do
and let r be the interest rate expressed as a decimal. Since
Yn is the amount owing at the start of the nth year the end repay_loan

*
Omit if you don’t have time

9
Test the program with Y1=100, r=10% and N=2, check by 121 read(*,*) x
hand. if (x<=0) then
write(*,*) ‘input must be positive, please try again’
Try other values and see if they seem reasonable. goto 121
end if

Task 12 - solve f(x) = 0 by iteration


Originally FORTRAN programs contained many goto
Newton’s iterative scheme to solve f(x)=0 is given by: statements and labels, however this can make the program
f ( xn ) hard to follow. In more recent languages the goto and label
x n+ 1 = x n − You may or may not have seen this are almost extinct. We will try and do without them as
f′ ( xn )
much as possible as they are considered to be bad practice.
before. It is not essential for this exercise that you are However there is one situation where a goto is unavoidable,
familiar with this formula. this is when we have to deal with input errors.
For example if N is declared as an integer and in response
To solve x + 4 x + x + a = 0 the iterative scheme is
3 2
to read(*,*) N we type in a real decimal number eg 2.1 or a
given by letter then the program will stop and an error message will
( x n3 + 4 x n2 + x n + a ) be generated. You may already have come across this in
x n+ 1 = x n − some of your programs. To gain control of this situation
(3x n2 + 8x n + 1) FORTRAN provides the following:

Write a program similar to that in task 11. In this problem: read(*,*,err = label) N

• Y1= x1 , the starting value for the iteration. Thus if an error occurs when inputting N the program will
not crash but will go to the statement with the given label.
• Y= x n+ 1
• N is the number of iterations to be carried out
• a is a parameter - initially look for solutions with a=-6

Thus an improvement on task 7 is:

program nice_input
real x
Run your program with N=5, a=-6 and a starting value of
Y1=1.5. Run it again but with Y1=-3.5 write(*,*) ‘input a positive number’
do
Run your program to find all the roots of the cubic: read(*,*,err = 121) x
x 3 + 4 x 2 + x − 1 = 0 correct to 3 decimal places. if (x>0) exit
121 write(*,*) ‘input must be positive, please try again’
end do
2.11 goto - label - read errors - continue end

label
One to five digits placed at the beginning of the line before task 13 *
a statement:
Amend task 7 as above. Run this program and try entering
121 write(*,*) ‘this statement has a label’ characters that are not positive numbers (ie letters or
negative numbers). You should find that the program will
goto not terminate until you have entered a positive number.
This command is used to send control to a labelled
statement As labels can only be attached to statements and not, for
example, to declarations:
goto 121 121 real x is illegal
We introduce the dummy statement continue.
When this statement is encountered the program jumps to
the statement labeled 121, executes the statement then Thus using:
continues from that point on. 121 continue enables us to jump to
this point in the program and then continue on from that
The following code was previously executed using an point.
unbounded do (see task 7) which is much neater and does
not use a label and a goto
Task 14 - program prime - the function real(N)
write(*,*) ‘input a positive number’

10
Write a program to input an integer N greater than 2, test to
see if its prime and output a suitable message. The control structure of this program is more complex than
any encountered so far. It contains an If then else
A simple algorithm to test if a number is prime is to first to structure which itself, in the else part, contains a do loop
check that it is not even and then to see if it is divisible by which in turn contains an if then structure. Note that each
any of the odd numbers from 3 to N Theoretically this of the structures has its own end statement. (naming
should work, however there are two problems: individual control structures can help you to follow the flow
of the logic in the program, though I haven’t used names
a) the FORTRAN square root function only takes real types here))
as its argument. Thus the integer value N has to be
converted to a real type. This is done using the function The exit statement is used to get us out of the do loop as
real(N) Thus instead of writing sqrt(N) which would soon as we find a factor.
give an error we write sqrt (real (N) )
2.13 Task 15*
b) the FORTRAN square root function returns a real It is rumoured that the quadratic N 2 − N + 41 generates a
answer, thus there may be a round off error. For prime number for each of the integers N from 1 to 40.
example if N=49 then it may happen that Amend program prime to calculate the values of this
49 = 6.9999999 and we would only test N for quadratic for N=1 to 40, check to see if each value is prime
factors of 3 and 5 and hence declare 49 to be prime. To and output a suitable message for each value.
overcome this problem we will see if N is divisible by
all odd numbers from 3 to N + 1

Complete and test the following program:

program prime
integer N, I, remainder

by adapting the program nice_input above write code to input


an integer greater than 2

! Test to see if even


if (N-2*(N/2) ==0) then
write(*,*) ‘ the number is even - not prime’
else
! Test to see if divisible by odd numbers 3 - N + 1
do I = 3, sqrt(real(N)) + 1, 2
remainder = N-I*(N/I)
if(remainder==0) then
write(*,*) output suitable message
exit
end if
end do
end if

! write code to output suitable message if remainder never


zero

end prime

2.12 details of program prime

N-I*(N/I) This tests to see if N is divisible by I.


Try it with some numbers and you will see that it produces
the remainder on dividing N by I, provided you carry out the
N/I quotient using integer division.(see 1.9)
It is used in the first instance with I=2 to test if N is even
and then with I odd from 3 to N + 1.

11
Chapter 3 program distance
! declare function types
Subroutines and Functions real dist
!declare other variables
3.1 Introduction real x1,y1,x2,y2,d
!input data
FUNCTION write(*,*) ‘input the X- co-ordinates of two points’
You have already encountered some of FORTRAN’s read(*,*) x1,x2
intrinsic (built-in) functions such as sqrt(x) and sin(x), in write(*,*) ‘input the Y co-ordinates of two points’
this section we look at how to define our own functions. In read(*,*) y1,y2
general a FORTRAN function, like a simple mathematical ! invoke function
function, takes any number of arguments and returns a d=dist(x1,y1,x2,y2)
single value. Thus, for example, we can define a function !output result
called dist that will calculate the distance between two write(*,*) ‘distance between the points = ‘, d
points in two dimensions, it will have four arguments for the end distance
co-ordinates of the points and will return a single real value.
Thus d=dist(x1,y1,x2,y2) will calculate the distance function dist(x1,y1,x2,y2)
between the two points (x1,y1) and (x2,y2) and place the real dist,x1,y1,x2,y2
result in d. dist= sqrt((x2-x1)**2+(y2-y1)**2)
It is usual practice not to allow the function to change the end dist
values of the arguments or to execute any input or output
routines

SUBROUTINE - call
A subroutine is a more versatile form of a function, like the 3.3 Task 17 - Newton’s Method
function it can have several arguments, however it is
capable of returning more than one value. For example we We now return to the problem in task 12, that of solving
may wish to calculate the volume and surface area of a f(x)=0 using Newton’s method. The general formula for the
f ( xn )
rectangular box given its height, length and breadth. If we method is given by: x n+ 1 = x n −
refer to the subroutine as sizebox then it would appear in f ' ( xn )
the programme as :
call sizebox (height,length,breadth,volume,area) This task asks you to write a program that will :
In this case the first three parameters are the data and the
last two return the required results after this statement has • Input the initial value of x, an accuracy value and a
maximum number of iterations, refered to respectively
been executed. The word call is a special FORTRAN word
in the program as : y1, accuracy and MaxIt .
that is used with subroutines
• Implement the functions f (x) and f ‘(x) as user
We can also use subroutines to execute detailed input and defined FORTRAN functions. Clearly for each
output routines. problem you will have to write new functions
• The iterative process should continue until the
3.2 Task 16 - Creating a Function difference between x n and x n+ 1 is less than the
variable accuracy or the maximum number of iterations
So far our programs have only contained one segment, has been exceeded. To compute the difference
namely the main program segment. Functions and between x n and x n+ 1 you should use
subroutines appear after the main segment as separate
pieces of code. The following program illustrates the | x n + 1 − x n | which with the variables below will be
definition and use of a function. coded as abs (Y-Y1). The program uses the variable
Note that in the main program segment the function name count to count the number of iterations performed.
dist is declared as real since the function is to return a real • Output a suitable message, depending on whether or
value. The function segment itself appears after the main not the program terminated because it exceeded MaxIt
segment and in general looks like: or because it reach the required accuracy.

function name (variable list) Complete, as above, the following skeleton program to
declare function type and variable type
solve f (x) = 0 where f ( x ) = sin( x ) − x x ≠ 0.
2
… … … … … … … … …
… … … … … … … … … …
end [name]

12
Program newton task 19 - creating a subroutine
! f and derivf are the function names of f and f ‘
real f,derivf The following program illustrates the simple use of a
! y1 current value of x and y next value of x subroutine to calculate the volume and surface area of a
real y1,y,accuracy,difference rectangular box given its height, length and breadth.
integer :: count=0, MaxIt
Note that unlike the function:
write code to input y1, accuracy and MaxIt • the subroutine is used to return several values. These
may be of different type, though here they are all real.
iterate: do • the FORTRAN word call is used to implement the
y = y1-f(y1)/derivf(y1) subroutine.
count=count+1 • the subroutine name is not a data type, (e.g. real or
difference=abs(y-y1) integer) and therefore it is not necessary to declare it

construct a simple if statement that will exit the do loop if Note that like a function :
count >= MaxIt or difference < =accuracy • we can use dummy variables in the definition of the
subroutine
y1=y
end do iterate program box
real height, length, breadth, volume, area
write code to output the answer if the required accuracy is write(*,*) ‘input the height, length and breadth of the box’
achieved within the maximum number of iterations or a read(*,*) height, length, breadth
suitable message if not call sizebox (height, length, breadth, volume, area)
write(*,*) ‘volume =’ , volume, ‘area = ‘, area
end newton end box

function f(x) subroutine sizebox (ht, len, brdth, vol, area)


write code for the above function real ht, len, brdth, vol, area
end f vol = ht * len * brdth
area=2*(ht*len + ht*brdth + len*brdth)
function derivf(x) end sizebox
write code for the derivative of the above function
end derivf Run the program with suitable input and check your results.

NB In the definition of the functions I have used x as task 20 - input/output with a subroutine
the variable, any name is permissible provided you continue
to use it inside the function segment. When we use the As mentioned in the introduction to this chapter it is
function as f(y1) then the value of y1 replaces x in order to considered bad practice to carry out any input or output
evaluate f(y1). In this context x is called a dummy variable. within a function, or change any of the variables passed to
a function. Only the main segment or subroutine segments
Run your program with y1 = 0.5 , MaxIt = 10 and accuracy should be used for these purposes. In program box, and
= 0.01 indeed many of the above programs it would have been
neater to put all the i/o in a single subroutine. Write a
task 18 * subroutine called nice_input(ht,len,bdth) that will ONLY
Amend task 17 to print out the values of x n and the input positive real values. Refer back to section 2.11 and
variable difference as you iterate. Solve task 13 to see how this can be done.

f ( x ) = sin( x ) − x 3 + x 2 = 0 , x ≠ 0 correct to three Add you subroutine to the program box and replace the
decimal places. This problem has two solutions, one existing input statements with a call to it. Test your
negative and the other positive. program.

You may also wish to improve your program by trapping any


possible occurrence of f '( x ) = 0

13
b
task 21 - numerical integration
∫f ( x) dx
a
program Integrate
real :: h, a, b, x, f, Intgl=0
integer i, N
We now consider a problem in which we use both
subroutines and functions. First we look at the write code to input the limits a and b and the number of
mathematical problem of approximating the value of a strips N. You may wish to do this in a separate subroutine
definite integral of a given function over a given interval.
One of the most simplest methods is the trapezoidal rule ! initialise x = a and calculate h
which divides the interval of integration into parts and then x=a
approximates the area under the curve in each part using the h=(b-a)/N
area of a trapezium. See fig 1.
!carry out the summation
do I=1,N
1 call TrapInt(x,h,Intgl)
y = f ( x) =
1+ x2 end do

write code to output the result


S
end Integrate
V

function f(x)
T U
write code for f(x)
end f
x x+h

subroutine TrapInt(x,h,I)
Fig 1 real x, h, I

write code to update:


x+ h • I by adding to it the area of the trapezium in fig 1.
We approximate
∫f ( x) dx by the area of the trapezium
x
• x by adding h to it

h end TrapInt
STUV which is given by [ f ( x + h) + f ( x )] . Thus by
2
splitting the interval [a,b] into N strips each of width h we
can , by adding together all such approximations, obtain an
Use the above program to obtain an approximation to
b
1
approximation for
∫f ( x) dx .
a
∫1 + x
1
2
dx correct to two decimal places. i.e.increase the
0
The following program uses:
value of N until two answers agree to two decimal places
• a function for f (x) which we use as f(x) and f(x+h)
• a subroutine TrapInt(x,h,Intgl) which: Is this result correct?
a) calculates the approximation to the integral
on the interval [x,x+h]
b) adds the result to the existing value of Intgl
which already contains the integral from a to
x
c) moves x on to the start of the next interval.

By calling the subroutine TrapInt N times we will add


together all N trapeziums that make up the total area.

Although we will have to change the function routine for


f(x) for different integrals we can input the interval [a,b]
and the number of strips N at run time.

14
Chapter 4
Task 22 Array assignment - do implied list
Arrays, Derived Types and Modules
Run the following program and convince yourself that you ar
4.1 Arrays - definition getting the correct output.

An array consists of a rectangular set of elements all of the program rank1_array


same type (any type can be used). In mathematics simple
examples of arrays are the components of a vector or the !declare two real arrays of rank 1 size (4) and integer I
elements of a matrix. The vector A with components A(1), real, dimension(4) :: A,B
A(2) and A(3) is defined in FORTRAN using the statement: integer I

real, dimension(3) :: A ! assign values to the two arrays A and B


do I=1,2
This statement declares 3 real variables denoted A(1), A(2) A(I)=I*I
and A(3) B(2*I-1)=3*I
B(2*I)=4*I
To refer to the elements of a matrix we require two end do
parameters one for the row position and one for the column. A(3)=0
Thus the element in the ith row and jth column of a matrix A(4)=0
1 2
B is denoted B(i,j). For example if B =   then write(*,*) ‘array A’ , (A(I),I=1,4)
3 4 write(*,*) ‘array B’ , B
B(1,1)=1, B(1,2)=2 , B(2,1)=3 and B(2,2)=4. In FORTRAN end program rank1_array
we would declare such a matrix as:
• I have used an integer expressions for the indices of the
real, dimension(2,2) :: B B array viz. B (2*I-1) and B(2*I) . This picks out the
odd and even indices respectively.
• The rank of an array is the number of parameters
required to reference one of its elements. In the above • The structure (A(I),I=1,4) is called a do implied list and
A is of rank one and B is of rank 2. is the same as writing A(1),A(2),A(3),A(4)

• An alternative way to write out an array is to just use the


An array of rank 3 could be defined by name as in: write(*,*) ‘array B’ , B

real, dimension(2,4,2) :: C Task 23 Order of Array - Nested do loop

The elements of C are in general referenced by C(i,j,k) or The following program:


specifically for example by C(1,2,1). Note that C contains • Assigns values to an array of rank 2
2 ×4 ×2 = 16 elements
• Writes out the array in a controlled way along the rows
so that the output to the screen gives the array as a
• The shape of an array is given by writing down the
matrix.
number of elements in each component. Thus the shape
of A is (3) the shape of B is (2,2) and the shape of C is
• Writes out the array in the order in which it is stored.
viz moving down the first column then the second and so
(2,4,2)
on.
In each of the above examples each of the indices starts at 1
Try running the program to observe the output.
and runs to the number indicated in the definition. For
example in C the first index runs from 1 to 2, the second
from 1 to 4 and the last index from 1 to 2. In each case the Program array_order
lower bound of the index is 1. Sometimes it is desirable to real, dimension(3,3) :: A
start the index at some other value, this can be done as integer I ,J
follows:
! Use nested do loop to assign values to the matrix
real, dimension(-1:2,3) :: D row_index: do I=1,3
column_index: do J=1,3
D is an array of rank 2 and shape (4,3). Thus if we use A(I,J)=I*I+2*J
D(i,j) in our program the value of i can be one of -1, 0, 1 or end do column_index
2 and the value of j one of 1, 2, or 3 end do row_index
! output a row at a time
Since D is of rank 2 and its shape is (4,3) it is just a 4 × 3 do I=1,3
matrix. However its row reference runs from -1 to 2 rather write(*,*) (A(I,J),J=1,3)
than the usual 1 to 4 as one might expect for such a matrix. end do

15
! output in the natural order in which A is stored The subroutine InMatrix:
write(*,*) • Is written to input a rank 2 array of shape (dim,dim) (ie
write(*,*) A a square matrix)
end program array_order • Uses variable X , which has to be declared inside the
• Note that the two do loops are nested one inside the routine using the variable dim to determine its size.
other. The outer loop row index I is first set equal to 1 • Prompts the user to input the elements one row at a
and then the inner loop is executed with J=1, 2 and 3. time.
The outer loop index I is then increased to 2 and the
inner loop execution repeated. This continues until all Subroutine InMatrix(X,dim)
combinations of I and J have been exhausted integer dim,I,J
• The write(*,*) is used to output a blank line to make real, dimension :: X(dim,dim)
the output more readable write(*,*) ‘input a’ , dim, ’by’, dim, ’matrix one row at a time’
write(*,*)
do I=1, dim
4.2 Matrix Multiplication read(*,*) (X(I,J),J=1,dim)
end do
Definition write(*,*)
end subroutine InMatrix
If the I-K th element∗ of the matrix A is denoted A(I,K) and
the K-J th element of B is denoted B(K,J) then the:
N
I-J th element of AB is defined by ∑
K =1
A( I , K ) B ( K , J ) • The subroutine MatProd takes three arrays of shape
(dim,dim), forms the product of the first two and puts
the result in the third.
• For this definition to be valid the number of columns of
A must equal the number of row of B; this is denoted by • To implement the technique of forming a summation
N in the above definition. (see task 9) we need to first set every element of C to
• If B has only one column this becomes the definition of zero, this can be done with the statement C=0.
the action of a matrix on a vector. FORTRAN allows certain operations and assignment
with arrays but you need to be careful.
Example:

Subroutine MatProd(A,B,C,dim)
1 25 6 1 ×5 + 2 ×7 1 ×6 + 2 ×8
  = 
3 47 8 3 ×5 + 4 × 7 3 ×6 + 4 ×8 declare the real matrices shape (dim,dim) and integer dim
declare integers I, J and K to carry out the product
19 22
= 
43 50 !Initialise the matrix C equal to zero
C=0
Task 24 Program MatrixProd - passing arrays
construct a triple nested do loop to calculate the product AB
Construct the following program which uses three placing the result in C as you go.
subroutines, one for input, one for multiplying the two
matrices and one for output. These should be placed after end subroutine MatProd
the main program segment.

In particular you should note the way in which the arrays are • The subroutine OutMatrix is almost identical to the
passed to the subroutines. routine InMatrix but uses write statements rather than
read to transfer the data
Program matrixprod
real, dimension(3,3) : : A,B,C
integer :: dim=3 Subroutine OutMatrix(X,dim)
call InMatrix(A,dim)
call InMatrix(B,dim) declare X , dim and any other variable you use
call MatProd(A,B,C,dim)
call OutMatrix(C,dim) write(*,*) ‘the product of the above two matrices is:’
end program matrixprod write(*,*)

write code to output the matrix X row by row



using a similar do loop and do implied list as in InMatrix
When referring to the I-K th element of a matrix the first letter always
corresponds to the row position and the second to the column . Thus end subroutine OutMatrix
for example A (1,2) would be the element of A in row 1, column 2.

16
• Note how we have used a do loop to input the co-
ordinates of both P(1) and P(2) by referring to the points
Test your program with the example above. as P(I)%X and P(I)%Y and then letting I loop from 1 to
2.
Try the following exmple:
• Some programming languages use a . instead of the %
1 2 1 − 2 3 1 sign.
  
1 1 1  1 − 1 0 
  
0 1 − 1 1 − 1 − 1

4.3 Derived Types - type - %

We have so far only discussed real, integer and array types.


FORTRAN also allows complex types, character types,
pointer types and logical types. In addition FORTRAN Type in the program and run.
90/95 allows us to define our own types. This can be a
useful facility as it allows us to code in a much more logical Program dist2d
fashion which is a great advantage when writing long
programs. type point
real X,Y
Given two points in two dimensions consider: end type point

a) Calculating the distance between the two points integer I


b) Calculating the co-ordinates of their mid-point. real :: d=0
type(point) , dimension(2)::P
We introduce the data type point which consists of a pair of type(point) M
numbers. We then declare two variables, each of type
point, to represent the two points and a variable M, also of do I=1,2
type point, for the mid-point. . write(*,*) ‘input the X and Y coords of point number’ , I
read(*,*) P(I)%X, P(I)%Y
The following program inputs two points, calculates the end do
distance between them and the co-ordinates of their mid-
point d = sqrt((P(1)%X-P(2)%X)**2 + (P(1)%Y-P(2)%Y)**2 )
M%X=(P(1)%X+P(2)%X)/2
The new features of the program are: M%Y=(P(1)%Y+P(2)%Y)/2

• The creation of the data type using the word type write(*,*) ‘distance between points = ‘,d
The lines. write(*,*) ‘mid point at ‘, M%X,M%Y
type point end program dist2d
real X,Y
end type point
create a data type called point
4.4 Modules - use
• The line:
type(point) , dimension(2) :: P This seems like a good time to introduce the concept of a
module, most languages have something similar. In
declares two points , P(1) and P(2), each of which has FORTRAN we can, amongst other things, use a module to
an X and Y component declare variables and create types . The following problem
The line: uses a module to allow us to access our user defined type
type(point) M inside different program segments. That is to say inside the
main segment, subroutines and functions.
declares a single variable M with components X and Y.
Note how type(point) is used in the same way as we NB All modules must appear before the main program
might use real or integer. segment which as we have seen comes before the
subroutines and functions.
• To refer to the coordinate of the point P(1) we use the %
symbol. Task 25

The X coord is referred to as P(1)%X and the Y coord The following program rotates a triangle in two dimensions
as P(1)%Y. Similarly for P(2) and M through a given angle about the origin (see diagram). This
type of calculation is clearly of great value when writing
software with animated graphical output.

17
T(1)%P(I)%X = I
T(1)%P(I)%Y=I*I
end do
θ
! input the value of theta and convert to radians
write(*,*) ‘specify, in degrees, the angle of rotation’
T(2) read(*,*) theta
P (3) theta=theta*pi/180

T(1) ! rotate triangle T(1) and store result in triangle T(2)


P (2) call rotate(T,theta)
P (1)
!write results to screen
write(*,*) ‘The new co-ordinates are’
do I=1,3
write(*,*) ‘ X = ‘ ,T(2)%P(I)%X, ’ Y = ‘ , T(2)%P(I)%Y
end do

The program will: end program rotate_triangle

• Set up the co-ordinate of a triangle. For simplicity we


will allow the program to specify the triangle and not NB. To refer to the X component of the I th point of
the user. triangle T(2) we write T(2)%P(I)%X
• Ask the user to input an angle through which the
triangle is to be rotated
• Call a subroutine to calculate the new co-ordinates
• Output the result Subroutine rotate(T,theta)
! Declare the types of the subroutine arguments and integer I
use geom_objects
In the program we define, inside a module, the following type(triangle),dimension(2) :: T
types: real theta
integer I
• As in the above we define a type point to represent the
co-ordinates of the vertices of the triangle. !rotate the three points of triangle T(1) and store in T(2)
• A type triangle that consists of three variables of type do I=1,3
point. T(2)%P(I)%X=T(1)%P(I)%X*cos(theta) -
T(1)%P(I)%Y*sin(theta)
Module geom_objects T(2)%P(I)%Y=T(1)%P(I)%X*sin(theta) +
type point T(1)%P(I)%Y*cos(theta)
real X,Y end do
end type point
end subroutine rotate
type triangle
type(point) , dimension(3) :: P
end type triangle
• Before running the program look at the code that sets
end module geom_objects the position of T(1) and write down the co-ordinates of
its vertices .

NB The type triangle contains three points P(1), P(2) and • Enter the module, main program segment and
P(3) each of which has an X and Y component subroutine in that order and as a check run initially with
theta equal to zero. This should give the co-ordinate of
T(1).
program rotate_triangle
• Run with theta =45 and theta = -45. Are the new co-
! declare two triangles T(1) and T(2) and angle of rotation ordinates of P(1) equal to what you expect?
use geom_objects
type(triangle), dimension(2) :: T • Calculate a value of theta such that after rotation the
real :: theta,pi=3.1415927 side P(1)P(2) is parallel to the x-axis. Run your
integer I program to check this result. Repeat this exercise for
the other two sides of the triangle.
! create the co-ordinates of triangle T(1)
do I=1,3

18
Task 26 - Rotating Rectangle

Amend task 25 to deal with a rectangle rather than a


triangle.

You will need to:

• replace the type triangle with a type rectangle which


will require four points rather than three
• Declare two rectangles, R(1) and R(2) would be a good
choice
• Initialise the position of R(1). I suggest that you position
it on the x-axis with one corner at the origin, this will
make it easier for you to calculate the initial co-
ordinates of the corners.

Run your program and test with values of theta that give
known results. Eg θ = 0 , θ = 90 , θ = 180 .

19
Chapter 5 write(*,10) a, c, I
10 format(2F12.8, I5)
Input and Output
Note how the second * in the write statement has been
replaced with a label number that is attached to the format
5.1 Introduction statement.

We have seen that the commands read(*,*) and write(*,*) The format statement consists of the following:
are used to input data from the keyboard and output data to
the screen. Used in this form the facility is extremely basic, • label format ( list of instructions, called edit
we have very little control for example over where, on the descriptors)
screen, the output should be written or indeed how many
figures should be used to express a particular value. In • F indicates that the number to be output is a floating
addition we have only been able to read from the keyboard point number, i.e. one that has been declared using real
and write to the screen, we have no means of reading from
or writing to a file. (i.e. data held on a disc on the system • I indicates that the number to be output is an integer,
either on your U drive or on any other available drive) i.e. declared as an integer.

We now introduce two separate items: • F12.8 indicates that the output will take up 12 places
on the screen with 8 places being used for the decimal
• The concept of formatted read and write along with the part of the number and 4 for the decimal point, sign and
facility to use a file rather than the keyboard and the integer part of the number. In the example we have
screen. This is part of the FORTRAN standard. written 2 F12.8 , the 2 is inserted to indicate that the
first two number in the write list should be output in
• The concept of windows input and output. We will this style. As we see a and c are both declared as real
look at the idea of a dialogue box and a canvas. The and are the first two variables in the write list.
former will enable us to input data at a specific point on
the screen (you already do this when you log into the • I5 indicates that the output will take up 5 places on the
system, inputting your id and your password) and the screen.
latter enable us to draw graphs and pictures. The
implementation of these facilities is NOT part of the • If the number to be output is too small for the allocated
FORTRAN standard thus any program that contains slot FORTRAN will pack out with spaces or zeros
command that involve this type of input and output will
not be transferable to another machine that does not • If the number to be output is too large for the slot
support Salford FORTRAN. FORTRAN just outputs *s; not very helpful!

5.2 Format statement • If there are more items in the write list than edit
descriptors in the format statement then a new line is
To see that we have a need for controlling the output to the started and the format statement is started again.
screen consider the output from the following program:
Task 26 - formatted output to screen
program F_out
real a, c Amend the program F_out by including a label in the write
integer I statement and introducing the format statement as above.
a=1/7.0 Run to obtain the output which will be arranged on your
c=1/10000000.0 screen as follows:
I=1234
write(*,*) a, c, I 12 places 12 places 5 places
end program F_out 0 . 1 4 2 8 5 7 1 5 0 . 0 0 0 0 0 0 1 0 1 2 3 4

The three number are presented on the screen as follows: Note that the numbers are placed over to the right of their
allocated slot.
0.142857 1.000000E-07 1234
Task 27 - formatted input from keyboard
we have no control over the spacing between the numbers or
the number of figures that will be displayed. Note how the There is no task 27 as formatted input from the keyboard is
system has resorted to a standard floating point form for c NOT VERY PRACTICAL. For example:
because it could not express the number using only six
decimal places. To control the output we associate with read(*,10) a,c,I
each write statement a format statement which provides 10 format(2F12.8, I5)
information on how the data is to be written. The following
illustrates how this is done: would require the user to input the data to fit exactly into
the allocated slots, inputting spaces and zeros where

20
necessary. If you wished to input a=2.6 you would have to FILE= ‘tsk28.dat’ tells the computer that it must find or
type in space space 2.60000000 in order to fill the create the file tsk28.dat ∗ .
allocated 12 places with the point in the correct place.
• close(11) This tells the computer that we have
finished with the file that is associated with channel
number 11.
5.3 Read and Write to a FILE

In the same way that your program is saved to a disc in a file


we can save data from a program or alternatively read a file Task 28 read a file
to provide data for a program. We will finally get rid of the
last * in the read and write statements. Assuming that you have already run the program OutFile
amend it as follows to read the file tsk28.dat and print the
To use a file we need to: results to the screen.

• Identify the name of the file, giving its complete path if • Replace the statement:
necessary write(11,10) a,c,I with read(11,10) a,c, I

• Tell the system that we wish to use the file, this we refer • Write code to output the variables to the screen using
to as opening the file the existing format statement

• Associate individual read and write instructions with the You should of course get the results already observed in task
given file. It is possible to have more than one file open 26, the difference now is that they were created by one
at a time as well as using the keyboard and screen for program, stored and then at a later time retrieved and
input and output. written to the screen.

• When we have finished with the file we tell the system Task 29 create a file and read with Excel
that it is no longer required by closing the file
It is quite often necessary to create and save data and then
analyse it using a separate piece of software. With this in
The following program opens a file called tsk28.dat , the mind the following task is to create a set of points, save
dat extension is just to remind me that it is a data file. If the them to a file and then invoke Excel to read the file and plot
file doesn’t exist then one is created, if it does exist then it a graph of the data.
is made ready for reading and writing.
Complete the following and run.
Type in and run the following program
Program CubicExcel
Program OutFile
real a,c write code to define a type called point as in section 4.3
integer I
a=1/7.0 declare an array P(I)… P(50) of type point - section 4.3
c=1/10000000.0
I=1234 integer I
open(11,FILE=’tsk28.dat’) ! open file for output with channel number 11
write(11,10) a,c,I write code to open file - provide name for file
10 format(2F12.8,I5)
close(11) ! calculate the co-ordinates of the fifty points
end program OutFile
do I=1,50
P(I)%X=I/10.0 -2.5
The two key statements are: P(I)%Y=P(I)%X**3 - P(I)%X
write(11,10) P(I)%X, P(I)%Y
• open(11,FILE=’tsk28.dat’) 10 format(F12.8, 1X, F12.8)
end do
The number 11 is called the channel number and is
used to identify the file with the read and write write code to close file
statements that are used to access it. Thus instead of
write(*,10) we now have write(11,10) end program CubicExcel


The file will by default be placed or looked for in your home
directory on the U drive. However if for example the file is to be
created or read from using the A: drive then we would have written
FILE= ‘A:\tsk28.dat’ etc etc

21
• The origin for the graphics screen is in the top left hand
NB To separate the X and Y components of each point so corner, with the x co-ordinate running across the screen
that Excel can read them as separate pieces of data we have from 0 to 640 and the y co-ordinate running down the
(0,0) screen from 0 to 480 Outer boundary in diagram below.

• The command
clear_screen_area@(X1,Y1,X2,Y2,colour)
(X1,Y1)

will fill the area defined by the co-ordinates with the


given colour. See shaded area in diagram below. In the
program I have used it to completely fill the graphics
area with clear_screen_area@(0,0,640,480,bkcol) with
the colour specified by the value of bkcol. This gives us
(X2,Y2) a coloured ‘canvas’ of one colour on which to draw. In
Graphics window the program bkcol=2 which corresponds to green.
Without this command the canvas will be black.

(640,480) NB. all parameters must be of type integer


introduced a space between the two values. This is done in
the format statement using 1X. (for two spaces we would
use 2X etc )
• draw_line@(a,b,c,d,col) this will draw a line in the
colour given by col from the point (a,b) to the point
Open Excel and open your data file. Excel will treat it as a
(c,d). In the program we draw a line in red from
data file and will take you through a few options before
(100,100) to the point (300,400)
displaying on the work sheet. Excel will refer to ‘fixed
width columns separated with spaces’ as opposed to data
NB. all parameters must be of type integer
delimited using commas. Our data is of course the former
and you should select this option
task 30
Use the wizard to plot the data - ask tutor
Run the above with different values of bkcol and make a
note of the relationship between the colours and the colour
numbers that generate them.
5.4 Graphical Output to Screen

The Salford software supports many features for creating


task 31
windows, using buttons, menus and the mouse. Here we
introduce just a few ideas that enable us to draw a picture
Amend the above code to draw a polygon through the points
onto the screen. The first program below simply opens a
(100,100), (150,300), (300,400), (250,300) and (100,100)
graphics window and draws a line. The second program
making each side a different colour.
uses the idea of rotating a triangle seen in task 25 along
with the output to the graphics screen.
5.5 Animated output to screen
Try the following program:
One of the basic methods of animating a figure is to carry
program line
out the following steps:
integer :: bkcol=2,col=4
call vga@
• draw the figure
call clear_screen_area@(0,0,640,480,bkcol)
• delete the figure by redrawing it in the same colour as
call draw_line@(100,100,300,400,col)
the back ground colour
end
• draw the figure at its new position
• colours are referenced by numbers, in the simplest cases By repeating these steps the figure will appear to move
the numbers 0 to 15 are used. Here I have set bkcol=2
to give a background colour of green and col=4 to give a As you would expect there are many variations on this
drawing colour of red scheme plus other methods of creating animations.
• call vga@
The following program creates a triangle and then proceeds
This creates the graphics screen of size 640 long to rotate it about a fixed point.
by 480 down. This gives 307,200 points on the I have split it into logical segments and used derived types
screen that can be illuminated in one of the and a module.
available colours. (these points are called pixels)

22
type(triangle) Z
The following module defines type point and type triangle Z%P(1)%X=300;Z%P(1)%Y=250
as well as declaring and initialising integers for the Z%P(2)%X=400;Z%P(2)%Y=250
background colour (bkcol), the drawing colour (drcol) and Z%P(3)%X=350;Z%P(3)%Y=300
the point of rotation (x0,y0). end subroutine BasicTriangle

module geom
type point This subroutine rotates the basic triangle T(0) through theta
integer X,Y about (x0,y0) and places the result in T(2) Note in this
end type point subroutine T is defined to be the array of triangles T(0),
T(1) and T(2). T(1) is not used.
type triangle
type(point),dimension(3)::P subroutine rotate(T,theta)
end type triangle use geom
type(triangle),dimension(0:2)::T
integer ::bkcol=3,drcol=15,x0=200,y0=200 integer I
end module geom real theta
do i=1,3
T(2)%P(I)%X=(T(0)%P(I)%X-x0)*cos(theta)
- (T(0)%P(I)%Y-y0)*sin(theta)
T(2)%P(I)%Y=(T(0)%P(I)%X-x0)*sin(theta)
+(T(0)%P(I)%Y-y0)*cos(theta)
T(2)%P(I)%X=T(2)%P(I)%X+x0
This is the main segment and controls the program T(2)%P(I)%Y=T(2)%P(I)%Y+y0
Note how the items in the module are made available to it end do
via the statement use geom end subroutine rotate

This subroutine actually draws the triangle T in the colour


program rot_triangle specified by the integer col
use geom
type(triangle),dimension(0:2)::T When the program executes the statement draw_line the
real theta line is not immediately drawn to the screen but is held in
integer I memory. Drawing to the screen only takes place when the
computer has a bit of slack time. Thus we find that all the
!Create the basic triangle triangles are drawn at the end of the program which isn’t
call BasicTriangle(T(0)) much use as all we see it the last triangle to be drawn since
what happens, happens very quickly. To force the system to
! initialise T(1) and T(2) to be the same as T(0) draw immediately to the screen we use the subroutine
T(1)=T(0);T(2)=T(0) perform_graphics_update@().

! create drawing area Indeed I force the system to draw all the triangle it has
call vga@ stored up when the draw colour is not the background
call clear_screen_area@(0,0,640,480,bkcol) colour. This has the effect of deleting a triangle and then
drawing a new one.
!draw and animate
do i=1,100 The subroutine perform_graphics_update is provided for us
theta=0.1*i but needs to be included as an extra into our subroutine
call drawtriangle(T(1),bkcol) using include<windows.ins>
call rotate(T,theta)
call drawtriangle(T(2),drcol) subroutine drawtriangle(T,col)
T(1)=T(2) use geom
! slow down the graphics include<windows.ins>
do n=1,1000000 type(triangle)T
end do integer col
call draw_line@(T%P(1)%X,T%P(1)%Y,T%P(2)%X,T%P(2)%Y,col)
end do call draw_line@(T%P(2)%X,T%P(2)%Y,T%P(3)%X,T%P(3)%Y,col)
end program rot_triangle call draw_line@(T%P(3)%X,T%P(3)%Y,T%P(1)%X,T%P(1)%Y,col)
if (col/=bkcol)call perform_graphics_update@()
This subroutine creates the basic triangle which is later end
rotated. Note Z is a single triangle

Subroutine BasicTriangle(Z) If you manage to type in and run this program then
use geom you really should spend some time working out what

23
is actually taking place in the program. What is the
function of each segment and how it achieves its task.

It is not an exercise in typing!

The End

24

You might also like