- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Consider this code
program proba
implicit none
interface
subroutine thunk()
end subroutine thunk
end interface
type funptr
procedure(thunk),pointer , nopass :: f
end type funptr
type(funptr) :: farr(3)
farr(1)%f=>a
farr(2)%f=>b
farr(3)%f=>c
call farr%f()
contains
subroutine a()
print *, 'a'
end subroutine a
subroutine b()
print *, 'b'
end subroutine b
subroutine c()
print *, 'c'
end subroutine c
end program proba
If I compile this code with ifort 15.0.0 20140723 , the program prints only "a". Now, I think I have found somewhere in Metcalfs book that it is possible to access subobjects in an array of derived objects collectively, something like arr%a, instead of looping over the arr: arr(i)%a. However, in the code above, I am calling a subobject function pointer, apparently collectively since the compiler did not complain. I never knew this was possible, but the result is even more baffling. I would have expected that such an "array call" would in turn call each of the subobject functions separately, but what it does is calling only the first subroutine -- subroutine a(). Subroutines b and c are never invoked. I have used this syntax construct by accident, omitting a looping index in calls to farr(i)%f(). It looks very weird to me and I wonder if it is maybe a compiler's bug not to report such invocation. Is this anyhow possible within the Fortran standard?
Link Copied
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
My hunch is this is a bug in Intel Fortran compiler that doesn't catch the error on line #18 of your code. My take on the Fortran 2008 standard documentation, especially sections 12.5 and 6.4.2 and constraint C618, is such a reference is disallowed.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Todor K. wrote:
.. Now, I think I have found somewhere in Metcalfs book that it is possible to access subobjects in an array of derived objects collectively, something like arr%a, instead of looping over the arr: arr(i)%a. ..
And if anything, Modern Fortran Explained by Metcalf et al. says exactly the opposite in section 13.6.2 - not that they (as Dr Fortran would remind us) are the final authority, the standard is.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
FortranFan wrote:
Quote:
Todor K. wrote:
.. Now, I think I have found somewhere in Metcalfs book that it is possible to access subobjects in an array of derived objects collectively, something like arr%a, instead of looping over the arr: arr(i)%a. ..
And if anything, Modern Fortran Explained by Metcalf et al. says exactly the opposite in section 13.6.2 - not that they (as Dr Fortran would remind us) are the final authority, the standard is.
Really?
The code below works when compiled in gfortran 4.9.2
program blah
implicit none
type jacko
integer :: a
end type jacko
type(jacko) :: jackoarr(10)
integer i
do i=1,10
jackoarr(i)%a=i
enddo
print *, jackoarr%a
end program blah
As far as I remember, though, this syntax is very restricted and I would be very suprised to see that Fortran 2008 allows anything like the program which I pasted into the original message. Hey, but I'm all for Fortran becoming a LISP variant :)
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Todor K. wrote:
..
Really?
The code below works when compiled in gfortran 4.9.2 .. As far as I remember, though, this syntax is very restricted and I would be very suprised to see that Fortran 2008 allows anything like the program which I pasted into the original message. Hey, but I'm all for Fortran becoming a LISP variant :)
What does the code you show in this case have to do with the code in the original post? Also, is it possible for you to upgrade your gfortran version? v4.9.2 is rather outdated, especially when it comes to features from Fortran 2003 and 2008 standard revisions. You can retry your original code with v5.2 or 6.0 development version of gfortran and see how it rejects it. Additionally, change the component attribute of component a in type jacko in your program blah to be a POINTER, add an allocate statement for jackoarr(i)%a in the DO loop, and now try the print statement on line #13 and see how it gets rejected. You can then review the details for yourself and delve into the commonalities between dereferencing of derived type data components with POINTER attribute and procedure pointer components.
Separately, I don't think the relevant aspects here have changed between Fortran 2003 and 2008 or even 2015, so not sure what you are getting at with your Fortran 2008 comment. And what does any of this have to do with LISP?
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
I agree that C618 prohibits the original program. C1230 (If data-ref is an array, the referenced type-bound procedure shall have the PASS attribute) also blocks what is being attempted here. I will let the developers know.
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
FortranFan wrote:
Quote:
Todor K. wrote:
..
Really?
The code below works when compiled in gfortran 4.9.2 .. As far as I remember, though, this syntax is very restricted and I would be very suprised to see that Fortran 2008 allows anything like the program which I pasted into the original message. Hey, but I'm all for Fortran becoming a LISP variant :)
What does the code you show in this case have to do with the code in the original post? Also, is it possible for you to upgrade your gfortran version? v4.9.2 is rather outdated, especially when it comes to features from Fortran 2003 and 2008 standard revisions. You can retry your original code with v5.2 or 6.0 development version of gfortran and see how it rejects it. Additionally, change the component attribute of component a in type jacko in your program blah to be a POINTER, add an allocate statement for jackoarr(i)%a in the DO loop, and now try the print statement on line #13 and see how it gets rejected. You can then review the details for yourself and delve into the commonalities between dereferencing of derived type data components with POINTER attribute and procedure pointer components.
Separately, I don't think the relevant aspects here have changed between Fortran 2003 and 2008 or even 2015, so not sure what you are getting at with your Fortran 2008 comment. And what does any of this have to do with LISP?
You misunderstood the part of my original post you quoted. I stated that array-subobject referencing works under certain conditions. I also remarked that the original construct probably does not fit within the legal fortran framework (as confirmed by Lionel below)
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page