psmile_multimap_routines.F90

Go to the documentation of this file.
00001 !-----------------------------------------------------------------------
00002 ! Copyright 2010, DKRZ, Hamburg, Germany.
00003 ! All rights reserved. Use is subject to OASIS4 license terms.
00004 !-----------------------------------------------------------------------
00005 !
00006 ! !DESCRIPTION:
00007 !
00008 ! Implementation of subroutines and functions of psmile_multimap. This
00009 ! is extracted from psmile_multimap.F90 in order to avoid circular
00010 ! dependencies with psmile_reallocate.
00011 !
00012 !
00013 ! !REVISION HISTORY:
00014 !
00015 !   Date      Programmer   Description
00016 ! ----------  ----------   -----------
00017 ! 18.11.10    M. Hanke     extracted from psmile_multimap.F90
00018 !
00019 !----------------------------------------------------------------------
00020 !
00021 !  $Id: psmile_multimap_routines.F90 2751 2010-11-19 13:53:28Z hanke $
00022 !  $Author: hanke $
00023 !
00024 !----------------------------------------------------------------------
00025 
00026    subroutine init_multimap (this)
00027       use psmile_multimap, only : multimap
00028 
00029       implicit none
00030 
00031       type(multimap), intent(inout) :: this
00032 
00033       nullify (this%keys)
00034    end subroutine init_multimap
00035 
00036    subroutine free_multimap (this)
00037       use psmile_multimap, only : multimap
00038 
00039       implicit none
00040 
00041       type(multimap), intent(inout) :: this
00042       integer :: i
00043 
00044       if (associated (this%keys)) then
00045          do i = lbound(this%keys,1), ubound (this%keys,1)
00046             if (associated (this%keys(i)%values)) &
00047                deallocate (this%keys(i)%values)
00048          enddo
00049          deallocate (this%keys)
00050       endif
00051    end subroutine free_multimap
00052 
00053    subroutine add_pair (this, key, value)
00054       use psmile_multimap, only : multimap, key_type, init_keys
00055       use psmile_reallocate
00056 
00057       implicit none
00058 
00059       type(multimap), intent(inout) :: this
00060       integer, intent(in) :: key, value
00061       type(key_type), pointer :: temp_keys(:)
00062 
00063       if (.not. associated (this%keys)) then
00064          allocate (this%keys(key:key))
00065          call init_keys(this%keys(key:key))
00066       else if (lbound (this%keys,1) > key .or. key > ubound (this%keys,1)) then
00067          allocate (temp_keys(min(lbound (this%keys,1),key):max(ubound (this%keys,1),key)))
00068          temp_keys(lbound (this%keys,1):ubound (this%keys,1)) = this%keys
00069          call init_keys(temp_keys(min(key,ubound (this%keys,1)+1):max(key,lbound (this%keys,1)-1)))
00070          deallocate (this%keys)
00071          this%keys => temp_keys
00072          nullify (temp_keys)
00073       endif
00074 
00075       if (.not. associated (this%keys(key)%values)) then
00076          allocate (this%keys(key)%values(1))
00077          this%keys(key)%values(1) = value
00078       else if (.not. any (this%keys(key)%values == value)) then
00079          this%keys(key)%values => psmile_realloc(this%keys(key)%values, &
00080                                                  size (this%keys(key)%values) + 1)
00081          this%keys(key)%values(size (this%keys(key)%values)) = value
00082       endif
00083    end subroutine add_pair
00084 
00085    function get_num_values (this, key)
00086       use psmile_multimap, only : multimap, is_valid_key
00087 
00088       implicit none
00089 
00090       type(multimap), intent(inout) :: this
00091       integer, intent(in) :: key
00092 
00093       integer :: get_num_values
00094 
00095       if (.not. is_valid_key(this, key)) then
00096          get_num_values = 0
00097       else
00098          get_num_values = size (this%keys(key)%values)
00099       endif
00100    end function get_num_values
00101 
00102    function get_values(this, key, num_values)
00103       use psmile_multimap, only : multimap, is_valid_key
00104 
00105       implicit none
00106 
00107       type(multimap), intent(inout) :: this
00108       integer, intent(in) :: key, num_values
00109 
00110       integer :: get_values(num_values)
00111 
00112       if (.not. is_valid_key(this, key)) then
00113          continue
00114       else if (size (this%keys(key)%values) >= num_values) then
00115          get_values = this%keys(key)%values(1:num_values)
00116          return
00117       endif
00118 
00119       get_values = 0
00120    end function get_values
00121 
00122    function get_value(this, key, value_idx)
00123       use psmile_multimap, only : multimap, is_valid_key
00124 
00125       implicit none
00126 
00127       type(multimap), intent(inout) :: this
00128       integer, intent(in) :: key, value_idx
00129 
00130       integer :: get_value
00131 
00132       if (.not. is_valid_key(this, key)) then
00133          continue
00134       else if (size (this%keys(key)%values) >= value_idx) then
00135          get_value = this%keys(key)%values(value_idx)
00136          return
00137       endif
00138 
00139       get_value = 0
00140    end function
00141 
00142    subroutine init_keys (keys)
00143       use psmile_multimap, only : key_type
00144 
00145       implicit none
00146 
00147       type(key_type), intent(inout) :: keys(:)
00148 
00149       integer :: i
00150 
00151       do i = lbound(keys,1), ubound (keys,1)
00152          nullify (keys(i)%values)
00153       enddo
00154    end subroutine
00155 
00156    subroutine rm_key (this, key)
00157       use psmile_multimap, only : multimap, is_valid_key
00158 
00159       implicit none
00160 
00161       type(multimap), intent(inout) :: this
00162       integer, intent(in) :: key
00163 
00164       if (is_valid_key(this, key)) then
00165          deallocate (this%keys(key)%values)
00166          nullify (this%keys(key)%values)
00167       endif
00168 
00169    end subroutine
00170 
00171    function is_valid_key(this, key)
00172       use psmile_multimap, only : multimap
00173 
00174       implicit none
00175 
00176       type(multimap), intent(in) :: this
00177       integer, intent(in) :: key
00178 
00179       logical :: is_valid_key
00180 
00181       if (.not. associated (this%keys)) then
00182          continue
00183       else if (lbound (this%keys,1) > key .or. key > ubound (this%keys,1)) then
00184          continue
00185       else if (.not. associated (this%keys(key)%values)) then
00186          continue
00187       else
00188          is_valid_key = .true.
00189          return
00190       endif
00191 
00192       is_valid_key = .false.
00193 
00194    end function
00195 
00196    integer function get_num_valid_keys (this)
00197       use psmile_multimap, only : multimap
00198 
00199       implicit none
00200 
00201       type(multimap), intent(in) :: this
00202 
00203       integer :: i
00204 
00205          get_num_valid_keys = 0
00206 
00207       ! if there is at least one key
00208       if (associated (this%keys)) then
00209 
00210          ! for all keys
00211          do i = lbound (this%keys,1), ubound (this%keys,1)
00212 
00213             ! if the current keys has at least one associated value
00214             if (associated (this%keys(i)%values)) &
00215                get_num_valid_keys = get_num_valid_keys + 1
00216 
00217          enddo ! i
00218       endif
00219    end function get_num_valid_keys

Generated on 18 Mar 2011 for Oasis4 by  doxygen 1.6.1