- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
F95 gave us assumed-shape arrays which are great.
But we nearly alway need to compute the size to do anything with them.
If I want the last element for instance.
So I was wondering, has there been any thoughts for a Future language development (F201x) to add some king of relative indexing.
maybe:
real, intent(in) :: arr(:)
real x, z(2)
x = arr(>1) !Last element
x = arr(<1) !First element
z = arr(>2:2) !Last two elements with stride two
But we nearly alway need to compute the size to do anything with them.
If I want the last element for instance.
So I was wondering, has there been any thoughts for a Future language development (F201x) to add some king of relative indexing.
maybe:
real, intent(in) :: arr(:)
real x, z(2)
x = arr(>1) !Last element
x = arr(<1) !First element
z = arr(>2:2) !Last two elements with stride two
Link Copied
3 Replies
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Use LBOUND and UBOUND
x = arr(UBOUND(arr)) !Last element
x = arr(LBOUND(arr)) !First element
z = arr(UBOUND(arr)-2:UBOUND(arr):2) !Last two elements with stride two
Jim Dempsey
x = arr(UBOUND(arr)) !Last element
x = arr(LBOUND(arr)) !First element
z = arr(UBOUND(arr)-2:UBOUND(arr):2) !Last two elements with stride two
Jim Dempsey
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
As Jim Dempsey suggested, there are already intrinsic functions that do just what you want (although not in the fancy way you might expect).
The LBOUND/UBOUND functions return an array of indices by default. Which means, as an example, that the result of array(UBOUND(array)) is not a scalar but a slice.
If you specify the dimension (as a second argument), then the result of LBOUND/UBOUND is scalar.
If you want, you can simplify things a little bit by providing your own wrappers, as in the example below.
[fortran]implicit none
integer :: i, N = 13
real, allocatable :: a(:)
allocate (a(N))
a = [real :: (i, i = 1, N)]
print *, 'first: ', a(LBOUND(a))
print *, 'last: ', a(UBOUND(a))
print *, 'last two, etc.:', a(UBOUND(a,1)-2::2)
print *
print *, 'first: ', first(a)
print *, 'last: ', last(a)
print *, 'last two, etc.:', rstride(a, 2)
print *, 'last three, etc.:', rstride(a, 3)
contains
pure function first(a) result(x)
real :: x
real, intent(IN) :: a(:)
x = a(LBOUND(a,1))
end function
pure function last(a) result(x)
real :: x
real, intent(IN) :: a(:)
x = a(UBOUND(a,1))
end function
pure function rstride(a, s) result(x)
real, intent(IN) :: a(:)
integer, intent(IN) :: s
real :: x(s)
x = a(UBOUND(a,1) - s * (s - 1)::s)
end function
end
[/fortran]
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
John, thanks for pointing out my error of ommission of the ",1". I got sloppy there. The compiler would have caught this quickly.
Jim
Jim
Reply
Topic Options
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page