私が継承したいくつかのFortranコードを最適化しようとしています。これは実行に数日かかる非常に反復的なコードであり、私は実行時間を短縮するために努力しています。 VTune Amplifierによると、いくつかの関数とサブルーチンの実行時間を短縮した後、最新のボトルネックはfor_deallocationとfor_allocationです(特に1つのサブルーチンから呼び出されます)。私は、 'for_'が割り振りと割り振り解除の前に何を意味するのか、特に割り振られていないので、少し不明です。次のようにコードの概要は次のとおりです。Fortranはなぜfor_allocateまたはfor_deallocateに多くの時間を費やしますか?
module global_variables
double precision, allocatable :: input_values(:)
double precision, allocatable :: input_values2(:,:)
double precision, allocatable :: indices_array(:)
double precision, allocatable :: value_array(:)
double precision, allocatable :: final_result(:)
end module
subroutine func1()
allocate(...global values...)
do I=1,n
call func2(I)
end do
end subroutine func1
subroutine func2(I)
double precision, intent(in) :: I
double precision :: value, x
double precision, dimension(3) :: output_array
call find_Indices(x)
value_array = input_values(indices_array)
call calculations(value)
do j = 1,3
value_array = input_values2(indices_array,j)
call calculations(output_array(j))
end do
final_result = output_array * value
end subroutine func2
subroutine find_Indices(position)
indices_array = some calculation on position
end subroutine find_Indices
subroutine calculations(output)
double precision :: output
output = some calculation on value_array
end subroutine calculations
私は、その性質上、実際のコードをまとめるのではなく貼り付けることがありました。過度の割り当て/解放時間を持つサブルーチンはfunc2です。サブルーチンには割り当てステートメントはなく、グローバル値の再割り当てはありません。私に利用可能なドキュメントを使用して、私は割り当て/解放の前に 'for_'が何を意味するのか、func2でそれに多くの時間が費やされたのかを確かめることができませんでした。ヒープ上にすべての配列を配置することを指定したコードのサイズのため、配列をスタックに戻すことはできません。
for_allocate/for_deallocateの性質を理解できる人はいますか?あるいは、この機能がそれほど時間を費やす理由は?
SOLUTION:
アレイのプロパティをグーグルでいる間、私が持っていた別の問題のために、私はこの記事に出くわした: Fortran: dynamic arrays vs. automatic array Avoiding Memory Allocation
割付けグローバル配列を変更すると大きなオーバーヘッドがあることを示しています。 value_arrayを割り当て可能な配列からポインタ配列(double precicion、pointer :: value_array(:))に変更すると、for_allocateとfor_deallocateからオーバーヘッドの大部分が削除され、ランタイムがその1/5に短縮されました。これは、割り当て可能な配列の値が変更されると、元の配列の割り当てが解除され、新しい配列が割り当てられることを示しています。これはFortranのコミュニティではよく知られているかもしれませんが、新しいユーザーとしては、この動作に関するドキュメントの形式には触れていませんが、それは私には分かりませんでした。
いくつかのコンテキストが必要です。コンパイル可能なサブルーチン、少なくとも(より良いプログラムになります)、コンパイラを使用しています。 – Jack
より良い情報がない場合、func2への複数回の呼び出しで動的配列を保持し、スタックとヒープを試してみることが必要な場合があります。 output_arrayはコストのかかる割り当てでヒープに移動する可能性が最も高いようです。 for_は単にFortranランタイム・ライブラリーを指します。 – tim18
私はintel 17.0コンパイラを使用しています。私は、コンパイル可能な例の作成について私ができることを見ていきます。 私は、 'for_'がFortranの略であることに気がつきました。私は、IntelがFortranの略語として 'fort'を使用したという印象を受けました。 –