Section: BLAS/LAPACK - Dot Product#

Adapted from: gjbex/Fortran-MOOC

This program demonstrates performing a dot product in Fortran.#

Dot Products#

In this notebook we will use Fortran to perform dot products on vectors and matrices.

The dot product of two vectors in 3-space is given by:

\[ \Large \mathbf{u} \cdot \mathbf{v} = u_1 v_1 + u_2 v_2 + u_3 v_3 \]

where:

\[\begin{split} \Large \mathbf{u} = \left[ \begin{array}{c} u_{1} \\ u_{2} \\ u_{3} \end{array} \right] \end{split}\]

and

\[\begin{split} \Large \mathbf{v} = \left[ \begin{array}{c} v_{1} \\ v_{2} \\ v_{3} \end{array} \right] \end{split}\]

The approach makes use of the BLAS/LAPACK linear equation solver routine called SDOT. Information on this routine can be found at LAPACK - SDOT.

The driver program is called dot_test and is listed below:

In file dot_test.f90#

program dot_test
  implicit none
  integer, parameter :: v_size = 5
  integer :: i
  real, dimension(v_size) :: vector1 = [ (0.5*I, i=1, v_size) ], &
                             vector2 = [ (0.1*i, i=1, v_size) ]
  real, dimension(v_size, v_size) :: matrix = reshape( &
      [ (real(i), i=1, v_size*v_size) ], [ v_size, v_size ] &
  )

  interface
    real function sdot(n, sx, incx, sy, incy)
      integer :: n, incx, incy
      real, dimension(*) :: sx, sy
    end function sdot
  end interface

  print '(A20, *(F5.1))', 'vector 1: ', vector1
  print '(A20, *(F5.1))', 'vector 2: ', vector2
  print '(A20, F6.2)', 'vector1 . vector2 = ', &
      sdot(size(vector1), vector1, 1, vector2, 1)

  print '(A)', 'matrix:'
  do i = 1, size(matrix, 1)
      print '(*(F5.1))', matrix(i, :)
  end do
  print '(A, F10.1)', 'col 2 . col 4:', &
      sdot(size(matrix, 2), matrix(:, 2), 1, matrix(:, 4), 1)
  print '(A, F10.1)', 'row 2 . row 4:', &
      sdot(size(matrix, 1), matrix(2, :), 1, matrix(4, :), 1)
end program dot_test

The above program is compiled and run using Fortran Package Manager (fpm):

Build the Program using FPM (Fortran Package Manager)#

import os
root_dir = ""
root_dir = os.getcwd()

Since the code makes use of the LAPACK library, the following FPM configuration file (fpm.toml) was used:

name = "Section_BLAS_LAPACK_Dot"

[build]
auto-executables = true
auto-tests = true
auto-examples = true
link = ["blas", "lapack"]

[install]
library = false

[[executable]]
name="Section_BLAS_LAPACK_Dot"
source-dir="app"
main="section_blas_lapack_dot.f90"
code_dir = root_dir + "/" + "Fortran_Code/Section_BLAS_LAPACK_Dot"
os.chdir(code_dir)
build_status = os.system("fpm build 2>/dev/null")

Run the Program using FPM (Fortran Package Manager)#

exec_status = \
    os.system("fpm run 2>/dev/null")
          vector 1:   0.5  1.0  1.5  2.0  2.5
          vector 2:   0.1  0.2  0.3  0.4  0.5
vector1 . vector2 =   2.75
matrix:
  1.0  6.0 11.0 16.0 21.0
  2.0  7.0 12.0 17.0 22.0
  3.0  8.0 13.0 18.0 23.0
  4.0  9.0 14.0 19.0 24.0
  5.0 10.0 15.0 20.0 25.0
col 2 . col 4:     730.0
row 2 . row 4:    1090.0