Re: variable length of integer
- From: "jamesgiles@xxxxxxx" <jamesgiles@xxxxxxx>
- Date: Tue, 29 Apr 2008 13:59:18 -0700 (PDT)
On Apr 29, 7:48 am, John Appleyard <spamt...@xxxxxxxxxxxxxx> wrote:
...
Here's one I use - it has 2 different ways to compute the string length....
RealToString is altogether more complicated.
program testIntToString
print *,('"',inttostring(i),'",',i=-100,100)
contains
function IntToString(i) ! This version can be used in I/O statements
implicit none
integer :: i
character( max(1, int(log10(real(abs(i))+0.1)) + (3-sign(1,i))/2) )&
:: IntToString
integer :: val , p , izero=iachar('0')
if ( i<0 ) then
IntToString(1:1) = '-'
elseif ( i==0 ) then
IntToString(1:1) = '0'
endif
val = abs(i)
p = len(IntToString)
do while( val>0 )
IntToString(p:p) = achar(izero + mod(val,10))
val = val/10
p = p - 1
end do
end function IntToString
end program testIntToString
This will not work correctly on two's complement machines since for
the limiting negative value (-2^(p-1) for p bit integers) abs(I) is
still I, and is therefore still negative (either that, or your
implementation will detect overflow when ABS applied to that value and
halt the program). The procedure should read:
function IntToString(i)
! This version can be also used in I/O statements
implicit none
integer :: i
character( LenOfInt(i) ) :: IntToString
integer :: val , p , d
if ( i<0 ) then
IntToString(1:1) = '-'
endif
val = i
do p = len(answer), merge(2,1,i<0), -1
d = mod(val,10) + 10
! for MOD, the sign of the result is that of the
! first argument
IntToString(p:p) = "9876543210123456789"(d:d)
val = val/10
end do
end function IntToString
pure function LenOfInt(i)
integer :: i, LenOfInt
integer :: val
LenOfInt = 0
if (i<=0) LenOfInt=1
! when I equals zero, the loop below won't go
! even once. Yet the result must have room for
! at least one character.
! when I is less than zero, the following loop
! will go at least once, the the string length
! will always be 2 or more.
val = i
do while (val /= 0)
LenOfInt = LenOfInt + 1
end do
return
end function LenOfInt
The function LenOfInt is probably no better than your use of Log10 and
such, but yours is harder to prove correct. LenOfInt is a
"specification function" and must be PURE (and, as a practical matter,
must be a module function - it can't be an internal function!) I
would put both functions in the same module and make LenOfInt
PRIVATE. With the advent of F2003 implementations, and genuine
dynamic strings, it should be possible to rewrite the above without
the helper function and without exotic and hard to verify
specification expressions.
This procedure also doesn't depend on assumptions about the character
set. In particular, it does not assume that the digits are
consecutive in the native collating sequence. I don't know any
collating sequences where they aren't, and I vaguely recall that the
Fortran specification may require them to be, but why take chances.
The table look-up is probably faster anyway.
A note for CVF users: this kind of specification function (LenOfInt)
is supposed to work for the last version (CVF6.6c), but can be
problematical. I've found good results by making the LenOfInt
function appear after the IntToString function in the module. Other
things you might try is to put extra parentheses around the call to
LenOfInt in the declaration statement. Otherwise, CVF tends to get
lost and issues bogus messages, sometimes fatal. Evidently they've
got some convoluted logic in their parser where it applies static
semantic constraints and it sometimes gets lost.
Extra note: I typed this all in from memory (and to match the naming
conventions used by John Appleyard). I did not run the thing through
a compiler to check for syntax errors (I'm on travel and don't have a
compiler with me). As with anything you find on the usenet, verify it
before you just slap it into an important program. This lack of a
test is why I included some additional comments in the code to verify
to myself that I got some of the end cases correct.
--
J. Giles
"I conclude that there are two ways of constructing a software
design: One way is to make it so simple that there are obviously
no deficiencies and the other way is to make it so complicated
that there are no obvious deficiencies." -- C. A. R. Hoare
.
- Follow-Ups:
- Re: variable length of integer
- From: John Appleyard
- Re: variable length of integer
- From: jamesgiles@xxxxxxx
- Re: variable length of integer
- References:
- variable length of integer
- From: rudra
- Re: variable length of integer
- From: Clive Page
- Re: variable length of integer
- From: Richard Maine
- Re: variable length of integer
- From: John Appleyard
- variable length of integer
- Prev by Date: Re: Allocatable arrays in derived types
- Next by Date: Re: variable length of integer
- Previous by thread: Re: variable length of integer
- Next by thread: Re: variable length of integer
- Index(es):