Open jacobwilliams opened 5 years ago
@jacobwilliams wrote:
I want to be able to define a function that behaves like, for example, the intrinsic
SIZE
function, where the kind of the output is specified by an optional input. Am I correct that this currently isn't possible? ..
The specific example with 'my_class_size' function above is not feasible since KINDs need to be known at compile time. However, based on further description of the need, it may be possible to workaround it by designing the 'my_class' as a parameterized derived type.
Anyways, the need "I want to be able to define a function that behaves like, for example, the intrinsic SIZE function" is yet another instance where the Fortran standard makes certain allowances for intrinsic procedures (generic like ABS, FINDLOC, etc; variadic like MAX, MIN) and intrinsic types that are inextensible, single-component like C_PTR, etc. but does not extend the same courtesy for user procedures and types
This really comes to 'bite' because the committee refuses to include certain intrinsic 'classes' (a la what other languages now already have e.g., C++ in STL with std::string, std::vector, std::variant) that are so badly needed in the language but then there is extreme recalcitrance to offer to coders all the tools and mechanisms they need to build their own such 'classes'.
I have stumbled into this a few times already. The last time was in a discussion of extending the intrinsic character functions like verify
and scan
to a custom string type (see https://github.com/fortran-lang/stdlib/issues/321).
Allowing a mechanism to allow a kind
attribute in functions would make it much more convenient to use custom derived types (floats, strings) or types supporting automatic differentation (see #95), by allowing to overload all the intrinsic functions which have such an optional kind argument.
For a specific example say I want to use a derived type designed to emulate quadruple precision (106 bits of significand) using two doubles (also known as double-double arithmetic) or potentially the more ambitious quad-double (unevaluated sum of 4 doubles):
type :: dd_real
real(dp) :: x, y = 0.0d0
end type
To allow easily porting code from double to double-double, I would like to overload the real(a [,kind])
function, to cast down to a standard real
value (say for output):
pure function real(a,kind) result(y)
type(dd_real), intent(in) :: a
integer, kind, optional :: kind
real(kind=kind) :: y
block
intrinsic :: real
y = real(a%x,kind=kind)
end block
end function
If no optional argument is present, then kind
should resolve to the default type (and not a null pointer). Maybe this is something which could be pursued in connection to issue #22 (default value for optional arguments) and the related proposal #175. In that case, the default real kind could be set using
integer, kind, default(kind(1.0)) :: kind
Is there any way to find out if any related proposals have been discussed previously, and if yes, why were they rejected?
cc @certik @milancurcic @wclodius2 @sblionel
@ivan-pi , I don't recall ever seeing a proposal along these lines. It's an interesting idea.
I think this proposal is very similar to #128.
Similar, but not the same. size
returns an integer, but can be passed in any type. So there isn't an integer input to get the kind from. That's the kind of function I want to be able to write. There are couple other intrinsic functions that are not possible for a user to write (max
is another example)...see my other proposal at #76.
I want to be able to define a function that behaves like, for example, the intrinsic
SIZE
function, where the kind of the output is specified by an optional input. Am I correct that this currently isn't possible?Maybe using something similar to @cmacmackin's parameterized function syntax from #4, combined with a better way to specify the default value of optional arguments (see also #22):
See also #78, and also the various issues about generic programming and templates.