7

在 python 中(使用 numpy),我可以将数组广播到不同的形状:

>>> import numpy as np
>>> a = np.array([2,3,4])
>>> b = np.zeros((3,2))
>>> b[:,:] = np.zeros((3,2))
>>> b[:,:] = a[:,np.newaxis]  #<-- np.newaxis allows `a` to be "broadcasted" to the same shape as b.
>>> b
array([[ 2.,  2.],
       [ 3.,  3.],
       [ 4.,  4.]])
>>> c = np.zeros((2,3))
>>> c[:,:] = a[np.newaxis,:]
>>> c
array([[ 2.,  3.,  4.],
       [ 2.,  3.,  4.]])

有没有办法在fortran中达到同样的效果?我有一个子例程,它期望2D传入一个数组——我想将我的一维数组“广播”到二维,正如我在上面演示的那样。看起来很重要,我的二维数组确实有一个明确的接口。

作为旁注,我认为这个功能可能是由reshape内在提供的, - 类似于:

real,dimension(3) :: arr1d
reshape(arr1d, (/3,3/), order=(/1,/1))

但在阅读文档后,我认为这是不可能的,因为order似乎需要包括所有数字 1 到“N”。

编辑:为了更清楚一点,我正在寻找一种简单的方法来在输入上创建几个转换,a例如:

情况1

b(i,j) .eq. a(i)  !for all j, or even just j=1,2

案例2

b(j,i) .eq. a(i)  !for all j, or even just j=1,2

任意维度的加分1 :

b(i,j,k) .eq. a(i,j)
b(i,k,j) .eq. a(i,j)

等等

1免责声明——我实际上并没有给回答者加分的超能力;-)

4

2 回答 2

6

我不确定您要完成什么,但这里有几个片段可能会有所帮助。

reshape可以采用一个可选参数,称为pad,当您重塑为具有比您开始时更多的元素的数组时(例如从 3x4 到 2x4x2),该参数可用于提供所需的“额外”元素。

您可能还对spread为“提升”数组而设计的函数感兴趣,该函数将一个 rank-N 数组放入并输出一个 rank-N+1 数组。第二份副本中的片段可以重写为

array2d = spread(array1d,2,2)

在此示例中,第二个参数是沿其展开第一个参数以生成输出的维度。第三个参数是要制作的输入数组的副本数。

PS 调用spread应该是spread(array1d,1,2),我没有检查过。

编辑以回应OP对问题的编辑

通过分别跨维度 2 和 1 扩展来满足这两种情况,1 和 2。在 Fortran 中

b = spread(a,2,j)

b = spread(a,1,j)

由于spread返回一个秩 1 大于其第一个参数的秩的数组,因此它提供了所寻求的任意维度。但是,由于显示 rank-3 及以上的数组非常占用空间,我不打算这样做。

于 2013-02-03T08:19:30.563 回答
1

reshape 内在函数将允许您将 1D 数组复制到 2D 数组。使用足够新的 Fortran 编译器,它们是一种指针技术。指针提供了第二种引用存储的方式,避免了复制。该方法是“指针边界重新映射”。一个例子:

program array_tst

  integer, dimension (4), target :: array_1d
  integer, dimension (:,:), pointer :: array_2d

  array_1d = [ 1, 2, 3, 4 ]

  array_2d (1:2, 1:2) => array_1d

  write (*, *) array_2d (1,1), array_2d (1,2), array_2d (2,1), array_2d (2,2)

end program array_tst

另请参阅在 fortran 中更改数组维度

PS回复评论...如果您不介意复制数组,这里是如何使用reshape:

program array_reshape

  integer, dimension (4) :: array_1d
  integer, dimension (2, 2) :: array_2d

  array_1d = [ 1, 2, 3, 4 ]

  array_2d = reshape ( array_1d, [2,2] )

  write (*, *) array_2d (1,1), array_2d (1,2), array_2d (2,1), array_2d (2,2)

end program array_reshape
于 2013-02-03T03:09:38.127 回答