在 Fortran FMZM 多精度库中使用 IM_FORM 显示任意长度的格式化字符串

Display arbitrary length formatted string using IM_FORM in the Fortran FMZM multiple precision library

我正在查看 documentation for FMZM here,从第 8.(c) 部分,我了解到:

(c) Subroutine FM_FORM does similar formatting, but we supply a character string for
    the formatted result.  After declaring the strings at the top of the routine, as with
          CHARACTER(80) :: ST1,ST2
    the WRITE above could become
          CALL FM_FORM('F15.6',H,ST1)
          CALL FM_FORM('E15.7',T,ST2)
          WRITE (*,"(' Step size = ',A,'  tolerance = ',A)") TRIM(ST1),TRIM(ST2)
    FM_FORM must be used instead of FM_FORMAT when there are more than 200 characters
    in the formatted string.  These longer numbers usually need to be broken into several
    lines.

我需要使用 IM_FORM 函数来显示超过 200 个字符的大整数。在我的例子中,用 IM_FORM 代替上面的 FM_FORM。

之后,我看到一个声明:

character(200) :: str

和一些巧妙的格式设置:

str = IM_format( 'i200', result )   !<----- convert BigInt to string
print *, n, trim( adjustl(str) )    !<----- print huge integers

当我知道我的输出长度少于 200 个字符时,这很棒。但是,由于我使用的是任意精度库,所以很有可能我的数字要大得多。

所以工作形式类似于:

   character(2000)       :: str   
   res = mygetlargenumberfunction(n)
   call im_form('i2000', res, str)

我如何声明我的 character(?) :: str 变量和我的 IM_FORM 格式,以便我可以容纳在编译时未知的潜在更大的输出?我只能简单地猜测一个非常大的数字吗?

更新地址评论

我在 FMZM 任意精度库的上下文中处理分配和格式字符串,这就是它与被标记为重复的问题无关的原因。

改变

   character(2000)       :: str

   character (len=:), allocatable :: str

在所有其他条件相同的情况下,产生

Program received signal SIGSEGV: Segmentation fault - invalid memory reference.
...
Segmentation fault (core dumped)

所以这个建议似乎与 FMZM 不兼容。

使用gfortran -std=f2008 myprogram.F90

GNU Fortran (Ubuntu 7.3.0-27ubuntu1~18.04) 7.3.0

在@francescalus 的推动下,我这样解决了这个问题:

   ! 
   character (len=:), allocatable :: str
   character(len=1024) :: fmat
   !
   res = mygetlargenumberfunction(n)      ! call the function
   lenr = log10(TO_FM(res))+1             ! size the string
   allocate(character(len=lenr) :: str)   ! now allocate the string itself
   write (fmat, "(A5,I0)") "i", lenr      ! create the format string
   call im_form(fmat, res, str)           ! do the call
   print*, trim( adjustl(str))