简体   繁体   English

为什么这个 Fortran function 在打印两个 Hello World 之间需要永远

[英]Why this Fortran function takes forever between printing two Hello World's

The following Fortran function takes forever to print the Hello World 2 after printing Hello World 1 .以下 Fortran function 在打印Hello World 1后需要永远打印Hello World 2

program Test_Long_Run

    implicit none

    ! Variables

    integer,allocatable,dimension(:) :: test
    integer :: i, j, k, l, m, int
    
    allocate(test(1000*100)); test = 0
    ! Body of Test_Long_Run
    print *, 'Hello World 1'
    do k = 1,100
        do j = 1,100
            do i = 1,100
                do m = 1,100
                    do l = 1,1000
                        test(l*m) = 2
                        int = 2
                    enddo
                enddo
            enddo
        enddo
    enddo
    
    print *, 'Hello World 2'

end program Test_Long_Run

It runs very fast if I comment out test(l*m) = 2如果我注释掉test(l*m) = 2 ,它会运行得非常快

The instructions in the inner body perform 100 billion multiplication and assignments to a table, plus an assignment to a variable.内部主体中的指令执行 1000 亿次乘法和对表的赋值,以及对变量的赋值。 The array you write to contains 100 thousand integers, so does not fit into any cache.您写入的数组包含 10 万个整数,因此不适合任何缓存。 The elements you write to are not contiguous (stride: 1000*4 bytes), so each write must bypass/invalidate the cache and involve RAM.您写入的元素不是连续的(步幅:1000*4 字节),因此每次写入都必须绕过/使缓存无效并涉及 RAM。 This is slow.这很慢。 Even hundreds of processor cycles per each assignment.每个分配甚至数百个处理器周期。 If your processor runs at 2GHz, or at 2 billion instructions per second, you will make at most 10 million assignments per second.如果您的处理器以 2GHz 或每秒 20 亿条指令运行,那么您每秒最多将执行 1000 万次分配。 Now divide 100 billion by 10 million.现在将 1000 亿除以 1000 万。 10 thousand seconds?一万秒?

What happens if you remove the assignment to the array?如果删除对数组的分配会发生什么? The program will be left with an assignment to a single variable.程序将被分配给单个变量。 Assignment of a constant value.分配一个常数值。 A decent compiler will notice that all these loops can be thrown away and only one instruction will be left: int = 2 .一个体面的编译器会注意到所有这些循环都可以被丢弃,只剩下一条指令: int = 2

Remember that a compiler has a right to modify your source code if it decides that it will not change the program's behavior.请记住,如果编译器决定不会改变程序的行为,它就有权修改您的源代码。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM