2017-01-23 65 views
1

我有個1維工作陣列傳遞數組給需要不同形狀的子程序

real(8), allocatable :: work(:) 

其被傳遞到一個2維陣列

pure subroutine f(work, dim1, dim2) 
    real(8), intent(out) :: work(dim1, dim2) 
    integer, intent(in) :: dim1, dim2 
    ... 

上操作的子例程以下傳遞數組的方式有何區別?

call f(work, dim1, dim2) 
call f(work(1), dim1, dim2) 

他們是在同他們只是指針傳遞給第一個數組元素或者是有一些額外的開銷或者調用?現代Fortran中是否有更優雅的方式傳遞一個數組,其形狀需要改變,而不明確傳遞維度,但不會影響性能?

我知道上面看起來像舊的Fortran,但我發現它比宣佈父子程序二維陣列和傳遞一個數組部分,work(:dim1,:dim2),到f更快。

+0

在某種意義上,這裏有兩個完全不同的問題。 [1]](http://stackoverflow.com/q/25000321)'work'和'work(1)'.as參數有什麼區別? [2]](http://stackoverflow.com/q/24472907)如何將一個與啞元相關聯的形狀數組作爲另一個形狀? – francescalus

+0

對於你的最後一點,如果'work'是一個rank-2數組,那麼如果你將'work'作爲一個整體數組而不是數組部分'work(:dim1,:dim2)',那麼會發生什麼? – francescalus

+0

謝謝。在子程序內部,我正在做一些事情,比如用'work(:dim1,:dim2)'調用'dgemm''作爲參數之一。如果在調用作用域中將'work'聲明爲二維數組並且傳遞了完整數組,則這將導致自動創建一個臨時數組。重點是每個調用的維度可能不同,但我只分配一次工作空間。 –

回答

3

兩個示例語句是順序相關聯的形式。實際參數指定一個數組元素序列,然後按照數組元素順序與啞元參數的元素相關聯。

如果工作(在呼叫範圍)被分配給非零尺寸並具有較低的一個約束,有不太可能在執行實際的差異。

在這兩種情況下,程序員必須保證僞參數的尺寸必須小於或等於該實際參數元素序列的大小。

使用整個陣列參考使得它更清晰的讀者(或許還有編譯器),這是作者的意圖傳遞數組元素序列,潛在地包括該陣列中的所有元素。它也抵禦實際的論據是零大小,或者可能有一個以外的下限。

作者的意圖是遠不太清楚,當一個特定的元素的引用是用來指定的數組元素序列。

在此特定情況下,因爲實際的參數是可分配的編譯器知道實際的參數的元件序列將是連續的,並且它可以安排爲僞參數要具有適當的元件序列相關聯。在其他情況下,如果實際參數本身是沒有連續屬性的假定形狀參數,則編譯器不知道該元素序列是連續的,並且可能必須在調用之前複製元素序列。這可能會對材料性能產生影響 - 這可能就是爲什麼您發現使用非連續的rank 2數組部分作爲實際參數變慢的原因。

相關問題