compact_real_string Subroutine

private pure subroutine compact_real_string(string)

Arguments

TypeIntentOptionalAttributesName
character(len=*), intent(inout) :: string

Called by

proc~~compact_real_string~3~~CalledByGraph proc~compact_real_string~3 compact_real_string proc~str_r16p~3 str_R16P proc~str_r16p~3->proc~compact_real_string~3 proc~str_r4p~3 str_R4P proc~str_r4p~3->proc~compact_real_string~3 proc~str_r8p~3 str_R8P proc~str_r8p~3->proc~compact_real_string~3 proc~str_a_r16p~3 str_a_R16P proc~str_a_r16p~3->proc~str_r16p~3 interface~str~3 str interface~str~3->proc~str_r4p~3 interface~str~3->proc~str_r8p~3 proc~str_a_r8p~3 str_a_R8P interface~str~3->proc~str_a_r8p~3 proc~str_a_r4p~3 str_a_R4P interface~str~3->proc~str_a_r4p~3 proc~str_a_r8p~3->proc~str_r8p~3 proc~str_a_r4p~3->proc~str_r4p~3 proc~bctoi_i8p~3 bctoi_I8P proc~bctoi_i8p~3->interface~str~3 proc~bctoi_i2p~3 bctoi_I2P proc~bctoi_i2p~3->interface~str~3 proc~bctoi_i1p~3 bctoi_I1P proc~bctoi_i1p~3->interface~str~3 proc~bctoi_i4p~3 bctoi_I4P proc~bctoi_i4p~3->interface~str~3 interface~bcton~3 bcton interface~bcton~3->proc~bctoi_i8p~3 interface~bcton~3->proc~bctoi_i2p~3 interface~bcton~3->proc~bctoi_i1p~3 interface~bcton~3->proc~bctoi_i4p~3

Contents

Source Code


Source Code

   pure subroutine compact_real_string(string)
   !< author: Izaak Beekman
   !< date: 02/24/2015
   !<
   !< Compact a string representing a real number, so that the same value is displayed with fewer characters.
   !<
   !< @note No need to add doctest: this is tested by a lot of doctests of other TBPs.
   character(len=*),intent(inout) :: string      !< string representation of a real number.
   character(len=len(string))     :: significand !< Significand characters.
   character(len=len(string))     :: expnt       !< Exponent characters.
   character(len=2)               :: separator   !< Separator characters.
   integer(I4P)                   :: exp_start   !< Start position of exponent.
   integer(I4P)                   :: decimal_pos !< Decimal positions.
   integer(I4P)                   :: sig_trim    !< Signature trim.
   integer(I4P)                   :: exp_trim    !< Exponent trim.
   integer(I4P)                   :: i           !< counter

   string = adjustl(string)
   exp_start = scan(string, 'eEdD')
   if (exp_start == 0) exp_start = scan(string, '-+', back=.true.)
   decimal_pos = scan(string, '.')
   if (exp_start /= 0) separator = string(exp_start:exp_start)
   if ( exp_start < decimal_pos ) then ! possibly signed, exponent-less float
     significand = string
     sig_trim = len(trim(significand))
     do i = len(trim(significand)), decimal_pos+2, -1 ! look from right to left at 0s, but save one after the decimal place
       if (significand(i:i) == '0') then
         sig_trim = i-1
       else
         exit
       endif
     enddo
     string = trim(significand(1:sig_trim))
   elseif (exp_start > decimal_pos) then ! float has exponent
     significand = string(1:exp_start-1)
     sig_trim = len(trim(significand))
     do i = len(trim(significand)),decimal_pos+2,-1 ! look from right to left at 0s
       if (significand(i:i) == '0') then
         sig_trim = i-1
       else
         exit
       endif
     enddo
     expnt = adjustl(string(exp_start+1:))
     if (expnt(1:1) == '+' .or. expnt(1:1) == '-') then
       separator = trim(adjustl(separator))//expnt(1:1)
       exp_start = exp_start + 1
       expnt     = adjustl(string(exp_start+1:))
     endif
     exp_trim = 1
     do i = 1,(len(trim(expnt))-1) ! look at exponent leading zeros saving last
       if (expnt(i:i) == '0') then
         exp_trim = i+1
       else
         exit
       endif
     enddo
     string = trim(adjustl(significand(1:sig_trim)))// &
              trim(adjustl(separator))// &
              trim(adjustl(expnt(exp_trim:)))
   !else ! mal-formed real, BUT this code should be unreachable
   endif
   endsubroutine compact_real_string