Performance Fortran语言中的高性能查找表

Performance Fortran语言中的高性能查找表,performance,fortran,intel-fortran,Performance,Fortran,Intel Fortran,我的部分模拟代码要求我找到给定密度和温度的不透明度。对此没有分析关系;标准方法是使用2D数组,其中不透明度(i,j)对应于密度(i)和温度(j)的不透明度,并运行双线性插值以找到准确的不透明度 这是目前我小组代码中的瓶颈——每个时间步,插值例程在不同密度和温度下被调用大约1亿次,它占运行时间的20%。当前代码如下所示-有什么技巧可以改进它吗?我使用英特尔Fortran 16,选项为-O3-xavx-mcmodel=medium function smoothopc(den, temp, ig,

我的部分模拟代码要求我找到给定密度和温度的不透明度。对此没有分析关系;标准方法是使用2D数组,其中
不透明度(i,j)
对应于
密度(i)
温度(j)
的不透明度,并运行双线性插值以找到准确的不透明度

这是目前我小组代码中的瓶颈——每个时间步,插值例程在不同密度和温度下被调用大约1亿次,它占运行时间的20%。当前代码如下所示-有什么技巧可以改进它吗?我使用英特尔Fortran 16,选项为
-O3-xavx-mcmodel=medium

function smoothopc(den, temp, ig, opc, rhoT)

    implicit none
    real(kind=8), intent(in) :: den,temp 
    integer,intent(in) :: ig
    real(kind=8), intent(in), dimension(1:50, 1:50, 1:52) :: opc
    real(kind=8), intent(in), dimension(1:50, 1:2) :: rhoT

    real(kind=8) :: rho, te, smoothopc, r1, r2, t1, t2, &
            interpolation, denominator, a, b, c, d, opc11, &
            opc12, opc21, opc22, t, tp, r, rp

    integer :: rid,tid,i

    rho = den * 1d - 3          !g/cc
    te = temp / (1.6d - 19)     !eV
    tid = -1
    rid = -1
    do i = 1, 49
        r = rhoT(i, 1)
        rp = rhoT(i + 1, 1)
        t = rhoT(i, 2)
        tp = rhoT(i + 1, 2)
        if (rho .ge. r) then
            rid = i
        endif

        if (te .ge. t) then
            tid = i
        endif
    enddo

    r1 = rhoT(rid, 1)
    r2 = rhoT(rid + 1, 1)
    t1 = rhoT(tid, 2)
    t2 = rhoT(tid + 1, 2)
    opc11 = opc(rid, tid, ig + 4)
    opc12 = opc(rid, tid + 1, ig + 4)
    opc21 = opc(rid + 1, tid, ig + 4)
    opc22 = opc(rid + 1, tid + 1, ig + 4)

    denominator = (r2 - r1) * (t2 - t1)
    a = r2 - rho
    b = rho - r1
    c = t2 - te
    d = te - t1

    interpolation = a * (c * opc11 + d * opc12) + b * &
            (c * opc21 + d * opc22)

    smoothopc = interpolation / denominator

    return

end function smoothopc 

如果我理解正确,您正在对整个
rhoT
进行循环,以查找索引,然后在
opc
中查找值

如果对
rhoT
的列进行排序,那么编写二进制搜索可能会更快(这会带来开销,因此您必须进行测试)


另外,我不太理解您分配
rid
tid
(只有当
r试图分析此函数以找到瓶颈时,才分配rid似乎是合乎逻辑的。如果没有代码来调用具有代表性的数据,我们几乎不可能测试任何东西。使用一致的缩进将有助于查看代码的结构。请注意
kind=8
i它丑陋且不可移植。我不知道可以逐行分析函数-我使用gprof将此函数识别为整个代码中的瓶颈,但我如何具体获得有关此函数的更多信息?我不太喜欢
real(kind=8)
也可以,但我必须使用我得到的!有一些分析器可以分析单独的行,就像我最喜欢的Oracle Performance Analyzer(也适用于gfortran)。或者“英特尔vTune放大器”应该包含在您的“英特尔Fortran”中,学习如何使用它。请修复缩进,代码看起来非常糟糕。欢迎。我很少编辑其他人的答案,但我相信在这种情况下,标记来自OP代码的实体(变量名、函数名)会更加清晰作为代码,这样人们就不会对rid这个词感到奇怪。如果你不同意,你可以很容易地撤销编辑。