Skip to content

Full working example

Hani Andreas Ibrahim edited this page Jan 27, 2026 · 20 revisions

The following full working example program make use of

  • long and short options with and without arguments
  • long option without short equivalent (new in version 2.0.0)
  • automated checking for numbers in option's arguments
  • autmated checking for double options (new in version 2.0.0)
  • converting argument character output to numbers
  • mandatory options
  • error handling
  • help and version output

and is well documented.

Code

program f90getopt_mult
   ! Sample program for f90getopt version 2 or higher
   ! Multiplies alpha and beta

   ! Machine and compiler independent unit number for stderr (error output)
#ifdef f2003
   use, intrinsic :: iso_fortran_env, only : stderr=>error_unit
#else
#define stderr 0
#endif

   use f90getopt ! Provide f90getopt's features

   ! Local declarations
   implicit none
   double precision :: m1, m2               ! multiplier, multiplicand
   logical          :: a_present, b_present ! flags for mandatory options
   character(len=1) :: c                    ! getopt short variable

   ! Declaration of shortopts
   ! ----------------------------------
   ! - optshort  = character array of short option characters without a space
   !              colon ":" after a character says that this option requires an argument
   character(len=*),parameter :: optshort = "a:b:h"

   ! Declaration of longopts
   ! ----------------------------------
   ! option_s derived type:
   !   1st value = long option name (character array, max. 80)
   !   2nd value = if option has value (boolean)
   !   3rd value = short option name (single character), same as in getopt() or empty
   ! option_s is not needed if you just use short options
   type(option_s) :: optlong(4)
   optlong(1) = option_s("alpha",   .true.,  "a")     ! has argument
   optlong(2) = option_s("beta",    .true.,  "b")     ! has argument
   optlong(3) = option_s("help",    .false., "h")     ! has no argument
   optlong(4) = option_s("version", .false., char(0)) ! has no argument & no shortopt

   ! Local inits
   m1        = 0d0
   m2        = 0d0
   a_present = .false.
   b_present = .false.


   ! If no options were committed
   ! ----------------------------
   if (command_argument_count() .eq. 0) then
      write(stderr,*) "ERROR: Program has options. Use options -h or --help for details"
   end if

   ! Processing options
   ! ------------------------
   ! Process short options one by one and long options if specified in option_s
   !
   ! getopt(optshort, optlong):
   !  - optshort = character of short option character without a space
   !               ":" after a character says that this option requires a value
   !  - optlong  = longopts, if specified in option_s (optional)

   call check_duplicates(optshort,optlong)    ! Check for duplicates

   do
      c = getopt(optshort, optlong) ! shortopts & longopts declaration character

      ! When all options are processed
      if (c == achar(0) .and. optlongind == 0) exit

      if (c /= achar(0)) then
         select case(c)
            case("a") ! option -a --alpha
               a_present = .true. ! a is mandatory (if b is present)
               if (isnum(trim(optarg)) > 0) then ! Check for number in "optarg"
                  read(optarg,*) m1 ! Convert character string to double precision
               else
                  write(stderr,*) "ERROR: Option -a or --alpha is not a number."
                  stop
               end if
            case("b") ! option -b --beta
               b_present = .true. ! b is mandatory (if a is present)
               if (isnum(trim(optarg)) > 0) then ! Check for number in "optarg"
                  read(optarg,*) m2 ! Convert character string to double precision
               else
                  write(stderr,*) "ERROR: Option -b or --beta is not a number."
                  stop
               end if
            case("h") ! help output
               write(*, '(6(A/),/,4(A/))')&
                  "Usage: f90getopt_mult [options]",&
                  "Options:",&
                  "  -a X  --alpha=X   Multiplier",&
                  "  -b X  --beta=X    Multiplicand",&
                  "  -h    --help      Print this help screen",&
                  "  --version         Print version information",&
                  "Examples:",&
                  "  f90getopt_mult -a 5.2 -b 8.9",&
                  "  f90getopt_mult --alpha=5.2 --beta=8.9",&
                  "  f90getopt_mult -h --version"
         end select
      else
         select case(optlongind)
            case(4) ! version output (longopt w/o short equivalent)
               write(*,*) "Version 1.1.0"
         end select
      endif
   end do

   ! Processing and output of the data and result
   if (a_present .and. b_present) then ! both mandatory options are present
      write(*,*) "Result of ", m1, " * ", m2, "=", m1 * m2
   else if (a_present .and. (.not. b_present)) then
      write(stderr,*) "ERROR: Options -b (--beta) with argument is missing"
   else if (b_present .and. (.not. a_present)) then
      write(stderr,*) "ERROR: Options -a (--alpha) with argument is mising"
   end if

end program f90getopt_mult

Build

Put f90getopt.f90 and your sample program from above (let's say f90getopt_mult.F90) in the same directory and change to this directory with the cd command in the terminal (or Windows command prompt). Then type:

gfortran f90getopt.F90 f90getopt_mult.F90 -o f90getopt_mult

You can omit .exe in -o f90getopt_mult on Windows. Please be advised that the capital F90 file extensions are important to use the pre-processor directives.

Run

You can run it by e.g.:

  • ./f90getopt_mult -a 5.2 -b 8.9
  • ./f90getopt_mult -alpha=5.2 -beta=8.9
  • ./f90getopt_mult -h
  • `./f90getopt_mult --version

Clone this wiki locally