数组值数组索引

发布于 2024-10-12 10:03:21 字数 577 浏览 1 评论 0原文

我刚刚偶然发现编译器允许我使用整数数组作为其他数组的索引。例如:

  implicit none

  real*8 :: a(3), b(2)
  integer :: idx(2)

  a=1.d0
  idx=(/1,2/)

  b = a(idx)
  print*,shape(b) 
  print*,b
  print*

  end

鉴于这似乎适用于 gfortan 和 PGI 编译器,我想知道这是否是一种语言功能,而不是编译器让我使用的东西。如果比我更有知识的人可以评论这是否真的是一种语言功能,我将不胜感激。

如果是的话,如果有人能详细说明如何在多维情况下解释此类结构的确切语言规则,我将不胜感激,如下所示:

  implicit none
  real*8  :: aa(3,3), bb(2,2)
  integer :: idx(2)

  do i=1,3 ; do j=1,3
    aa(i,j) = 1.d0*(i+j)
  enddo; enddo

  bb=aa(idx,idx)
  print*,shape(bb)
  print*,bb

  end

I've just stumbled upon the fact that compiler lets me use integer arrays as indices to other arrays. For example:

  implicit none

  real*8 :: a(3), b(2)
  integer :: idx(2)

  a=1.d0
  idx=(/1,2/)

  b = a(idx)
  print*,shape(b) 
  print*,b
  print*

  end

Given the fact that this seems to work with both gfortan and a PGI compiler, I'm wondering if this a language feature rather than something compiler just lets me out with. I would appreciate if somebody more knowledgeable than me can comment if this is really a language feature.

And if it is, than I'd appreciate if somebody would spell out the exact language rules of how such constructions are interpreted in multidimensional case, like here:

  implicit none
  real*8  :: aa(3,3), bb(2,2)
  integer :: idx(2)

  do i=1,3 ; do j=1,3
    aa(i,j) = 1.d0*(i+j)
  enddo; enddo

  bb=aa(idx,idx)
  print*,shape(bb)
  print*,bb

  end

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

携余温的黄昏 2024-10-19 10:03:21

是的。

Fortran 2008 标准的最终草案,ISO/IEC JTC 1/SC 22/WG 5/N1830,ftp://ftp.nag.co.uk/sc22wg5/N1801-N1850/N1830.pdf 在第 84 页上说

4.8 数组值的构造

...

6 如果 ac 值是数组表达式,表达式元素的值,按照数组元素顺序(6.5.3.2),指定数组构造函数对应的元素顺序。

示例

real, dimension(20) :: b
...

k = (/3, 1, 4/)
b(k) = 0.0      ! section b(k) is a rank-one array with shape (3) and
                !  size 3. (0.0 is assigned to b(1), b(3), and b(4).)

您可以直接从代码输出中看到规则

implicit none
  real*8  :: aa(3,3), bb(2,2)
  integer :: idx(2),i,j,k
  idx=(/3, 2/)
  k=0
  do i=1,3 ; do j=1,3
    k=k+1
    aa(i,j) = aa(i,j)+1.d0*k
  enddo; enddo
  write(*,*),shape(aa)
  write(*,'(3G24.6,2X)') aa
  bb=aa(idx,idx)
  print*,shape(bb)
  write(*,'(2G24.6,2X)'),bb
  end

<前><代码> 3 3
1.00000 4.00000 7.00000
2.00000 5.00000 8.00000
3.00000 6.00000 9.00000
2 2
9.00000 6.00000
8.00000 5.00000

Yes, it is.

The final draft of the Fortran 2008 standard, ISO/IEC JTC 1/SC 22/WG 5/N1830, ftp://ftp.nag.co.uk/sc22wg5/N1801-N1850/N1830.pdf says on page 84

4.8 Construction of array values

...

6 If an ac-value is an array expression, the values of the elements of the expression, in array element order (6.5.3.2), specify the corresponding sequence of elements of the array constructor.

Example

real, dimension(20) :: b
...

k = (/3, 1, 4/)
b(k) = 0.0      ! section b(k) is a rank-one array with shape (3) and
                !  size 3. (0.0 is assigned to b(1), b(3), and b(4).)

The rules you can see directly from your code

implicit none
  real*8  :: aa(3,3), bb(2,2)
  integer :: idx(2),i,j,k
  idx=(/3, 2/)
  k=0
  do i=1,3 ; do j=1,3
    k=k+1
    aa(i,j) = aa(i,j)+1.d0*k
  enddo; enddo
  write(*,*),shape(aa)
  write(*,'(3G24.6,2X)') aa
  bb=aa(idx,idx)
  print*,shape(bb)
  write(*,'(2G24.6,2X)'),bb
  end

Output:

       3           3
         1.00000                 4.00000                 7.00000    
         2.00000                 5.00000                 8.00000    
         3.00000                 6.00000                 9.00000    
       2           2
         9.00000                 6.00000    
         8.00000                 5.00000
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文