To save content items to your account,
please confirm that you agree to abide by our usage policies.
If this is the first time you use this feature, you will be asked to authorise Cambridge Core to connect with your account.
Find out more about saving content to .
To save content items to your Kindle, first ensure no-reply@cambridge.org
is added to your Approved Personal Document E-mail List under your Personal Document Settings
on the Manage Your Content and Devices page of your Amazon account. Then enter the ‘name’ part
of your Kindle email address below.
Find out more about saving to your Kindle.
Note you can select to save to either the @free.kindle.com or @kindle.com variations.
‘@free.kindle.com’ emails are free but can only be saved to your device when it is connected to wi-fi.
‘@kindle.com’ emails can be delivered even when you are not connected to wi-fi, but note that service fees apply.
Use Fortran's C interoperability capabilities to interact with C programs.
Due to the enormous popularity of the C programming language (References [46], [38], and [28]), many Fortran programmers need to be able call routines written in C, or written to conform to C calling conventions. Likewise, it is often useful for C programmers to call routines written in Fortran. Beginning with Fortran 2003, there is a new and standard mechanism to allow easier and more portable interfacing between Fortran and C.
Here are some of the topics that must be considered when code written in Fortran accesses that written in C and vice versa:
The mapping of built-in data types between Fortran and C.
The mapping of pointers.
The mapping between Fortran derived types and C structs.
The mapping of global variables.
The internal calling sequence mechanisms for passing actual arguments and function return values during procedure calls.
The mapping of external names between Fortran and C and invocation of functions and procedures.
The next sections present details of these various points. The first deals with the mapping of the basic data types. Using these types, the second section presents the calling mechanism between the two, including mapping of external names; we present a short example. The sections that follow continue presenting the mapping of other types of entities, pointers, global data, and so on, also with short examples.
This paper presents a new algorithm to find the singularity-free cylindrical workspace of parallel manipulators. Because of the limited workspace of parallel manipulators cluttered with different types of singularities, a simple and robust technique to determine continuous singularity-free zones in the workspace of parallel manipulators is required. Here, the largest singularity-free cylinder within the workspace for any prescribed orientation ranging around a reference orientation angle of moving platform is determined. To this end, Particle Swarm Optimization is utilized to find the closest point on the singularity surface to the axis of the cylinder. By implementing the algorithm on 3-RPR planar parallel manipulator, the results show that this algorithm improves the efficiency and leads to significantly larger singularity-free workspace than those reported earlier.
We wrote this book for anyone who writes programs using Fortran. We think it will be useful for the following categories of programmers:
Those who are learning Fortran from scratch and want to start on the right foot.
Those who are familiar with pre-modern FORTRAN (up to FORTAN 77) and would like to learn some of the new concepts and techniques of modern Fortran (Fortran 90 to Fortran 2008).
Those who have advanced knowledge of Fortran, have experimented with various styles, and are open to new ways to improve their programs.
Those who have experience with other languages, who know the importance of good coding style and who want to apply it to their Fortran code.
Those who want to create coding guidelines for teams of programmers, or establish a good style for a project.
General Considerations
The past four revisions of the Fortran Standard comprise alternating major and minor revisions, Fortran 90 and Fortran 2003 being the former, Fortran 95 and Fortran 2008 the latter. This book concentrates primarily on Fortran 2003. We present Fortran 90/95 methods and note where the techniques and methods of Fortran 2003 supercede them. Fortran 2008 capabilities are described, but to a lesser extent.
Each programmer will judge the importance of the new features of the language based on his or her experience and needs. The new C Interoperability may be very important to a programmer who often needs to build an application written in both languages.
“The purpose of computing is not numbers. The purpose of computing is understanding.”
–Hamming
Write programs that are clear to both the reader and the compiler.
The first and foremost general principle of programming is clarity. From clarity comes the ability to test, to reuse, and to audit. One simple test is whether you believe you will be able to understand the code if you come back to it a year later.
Of course, you write programs to have the computer calculate something for you. And you know that the computer must be told exactly what to compute. Your program must completely and correctly specify what is to be computed.
If you are making a numerical calculation, you likely have some consideration for the efficiency of your calculation. The best way to gain efficiency is to first choose an efficient algorithm and then to write simple, clear, and logical code to implement it. Compared with more complex code, it is easier to understand and easier for the compiler to optimize.
In addition to writing code for the computer, you are also writing code for humans, yourself included. The purpose of the calculations and the methods used to do so must be clear.
To achieve these goals, write code that is as simple as possible. Use white space to aid your eye in following the calculation specified by the source code. Comment what cannot be understood from the code itself. The rules in this book follow from these ideas.
Until the advent of modern Fortran, the language could be classified as a strictly procedural one, built from subroutines and functions. A procedural program could be thought of as a series of calls to these procedures in which the desired computations are performed. Object-oriented programming, on the other hand, can be thought of as the interaction of independent entities, whereby the computations are carried out by means of messages sent and received by procedures (methods) bound to the entities (see Reference [8]).
Object-oriented programming (OOP) is a paradigm for programming that emphasizes the construction of objects that group related data. The objects are grouped with associated procedures and placed into a program unit, the module beginning with Fortran 90. Fortran 90 provided a limited capability for OOP, often referred to as “object-based” programming. Fortran 2003 provides the additional features that allow a programmer to program using object-oriented techniques. Some of the key features of OOP are (a) entities are constructed as objects. All objects are “instances” of what is commonly referred to as a “class,” which Fortran 90 introduced as “derived types.” These types define templates for the type data and its procedures. The placing of data in derived types is called “encapsulation.” (b) The procedures are referred to as “methods.” Execution of a program is carried out by objects communicating with each other by invoking the methods of other objects. This process is called “sending and receiving messages.”
Fortran 90 introduced free source form. We recommend that it always be used in new code. Free source form offers a number of advantages over the older fixed source form code:
Free source form is more compatible with modern interactive input devices than fixed form. The maximum line length is 132 characters, compared to the older limit of 72 characters. This reduces the possibility of text exceeding the limit, which could lead the compiler to misinterpret names.
Line continuations in free form are performed by using a trailing ampersand character, &, rather than entering a character in column 6 of the following line. As an additional visual reminder and safeguard, a leading ampersand, placed in any column, is also allowed to precede the remaining source code.
In fixed source form, the first six columns are reserved for statement labels, with column 1 also used to indicate comment lines. In modern code, using structured control statements, statement labels are rare. The first five columns are therefore wasted because they are rarely used. These last two features, combined with the next, provide much greater flexibility laying out the code.
The first section in this chapter explains the concept of “kinds” in Fortran. The second section presents several guidelines for using floating-point numbers in the context of performing numerical calculations using a representation that is by nature inexact. The third section presents some aspects of the floating-point exception handling that are now part of modern Fortran. Finally, in the fourth section we present some of the bit manipulation features.
The Concept of KIND
Modern Fortran characterizes the sizes and characteristics of integers, floating-point numbers and other data types as different kinds, and parameterizes them by kind type parameter values. For example, the Fortran processor will almost certainly provide a kind type parameter that corresponds to a four byte real. For one Fortran processor, the kind type parameter value may be 4, corresponding to the number of bytes; but, for a second processor, it could be 1, corresponding to the lowest precision available. The processor may also provide kind type parameters that correspond to single-byte, two-byte, and eight-byte integers.
The standard requires the processor provide at least one integer type. Similarly, two real kinds must be available. The default real kind is the less precise of the two. Normally, the default real will correspond to “single precision,” and the additional required kind to “double precision.” Thus, a processor may support several sizes of integers, each with a different kind type parameter value, and likewise for reals.
A common requirement when writing code is the ability to use the identical, or nearly identical, code for different data types. In the case of the public domain LAPACK linear algebra library (see Reference [5]), for instance, procedures support much the same set of operations for each of real, double precision, and complex data types. For example, the real version of a matrix operation routine might be identical to the complex version, except for a few details, primarily:
The data type of the dummy arguments.
The data type of function return values.
The data type of localized temporary variables.
Numeric constants (e.g., 1.0 vs (1.0,0.0)).
In addition to the data type, the kind and rank of arguments may also differ. A routine that processes real data may be identical to its double precision counterpart, thereby making the kinds different. And often routines accepting scalar arguments may need to be expanded to accept array arguments.
A number of techniques are used to make the job of generic programming easier and less error prone than simply replicating and hand-editing code. These techniques can be divided into three general methodologies: reducing the need to replicate code, reducing the number of code changes required to replicate code, and finally, automating the replication of code. The specific techniques we discuss are:
Use parameterized derived types to avoid replication based on kind and len.
Create and use generic names for procedures with interface blocks.
Adherence to no other guideline in this book will make your code more portable than adhering to this one. Over the years, compiler vendors and others have added numerous nonstandard extensions to the language. There is no guarantee that every compiler will support them or that any given compiler will continue to do so in the future.
When you write code that conforms to the standard, you can expect and demand that a “standard-conforming” compiler will successfully compile it. If it cannot, you have a good indication that either your code is in error, that it does not conform to the standard, or that there is a problem with the compiler itself. Most compilers can provide warning messages when encountering nonstandard code. If possible, do not depend on a single compiler as a reference. Compiling code through several different vendors' compilers can often expose additional errors. (See also Rule 4 and Section 15.3.)
Do not rely on compiler switches that change code semantics.
Many compiler vendors have added switches to their compiler directives that provide a capability that the programmer must otherwise provide by writing code. Some compilers, for example, have a switch that will automatically initialize all variables or change the default kinds of variables. Others have switches that remove the necessity for explicitly including the implicit none statement in every program unit. You should not use these; they make your code nonportable.