python 中周期性边界条件的有效符号函数
efficient sign function in python for case of periodic boundary conditions
我有 cython 代码,我正在使用它来加速纯 python 计算中的瓶颈。我在一个长度为 Lbox 的周期性盒子中有一对点(1d 的情况适合这个问题)。我需要计算 y-x 的符号,并且我需要在周期性边界条件起作用时翻转这个符号。
在没有 PBC 的情况下,以下问题提供了解决方案:Is there a standard sign function (signum, sgn) in C/C++?。该解决方案是我用来计算 sgn 函数的方法。
def sgn(x, y):
""" If x > y, returns 1.
If x < y, returns -1.
If x == y, returns 0.
"""
return (y < x) - (x < y)
下面写的sgn_pbc函数returns结果正确,但是写的效率低:[里面的控制流=30=]是拖慢PBC版本的罪魁祸首。我如何以类似于 sgn 函数的方式编写 sgn_pbc,从而避免笨拙的控制流程?
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
if d <= Lbox/2.:
return sgn(x, y)
else:
return -1*sgn(x, y)
首先,
-1*sgn(x, y) == sgn(y, x)
然后,
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
if d <= Lbox/2.:
return sgn(x, y)
else:
return sgn(y, x)
同样在 Python 中,函数调用是最昂贵的操作。您可以内联 sgn
.
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
if d <= Lbox/2.:
return (y < x) - (x < y)
else:
return (x < y) - (y < x)
但是 if
可以(大部分)重写为:
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
w = sgn(Lbox/2., d)
return w * sgn(x, y)
再一次,内联 sgn
,
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
w = sgn(Lbox/2., d)
return w * (y < x) - (x < y)
我说主要是因为 d == Lbox/2.
这个 returns 的值是错误的。
不过还没有计时。
我有 cython 代码,我正在使用它来加速纯 python 计算中的瓶颈。我在一个长度为 Lbox 的周期性盒子中有一对点(1d 的情况适合这个问题)。我需要计算 y-x 的符号,并且我需要在周期性边界条件起作用时翻转这个符号。
在没有 PBC 的情况下,以下问题提供了解决方案:Is there a standard sign function (signum, sgn) in C/C++?。该解决方案是我用来计算 sgn 函数的方法。
def sgn(x, y):
""" If x > y, returns 1.
If x < y, returns -1.
If x == y, returns 0.
"""
return (y < x) - (x < y)
下面写的sgn_pbc函数returns结果正确,但是写的效率低:[里面的控制流=30=]是拖慢PBC版本的罪魁祸首。我如何以类似于 sgn 函数的方式编写 sgn_pbc,从而避免笨拙的控制流程?
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
if d <= Lbox/2.:
return sgn(x, y)
else:
return -1*sgn(x, y)
首先,
-1*sgn(x, y) == sgn(y, x)
然后,
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
if d <= Lbox/2.:
return sgn(x, y)
else:
return sgn(y, x)
同样在 Python 中,函数调用是最昂贵的操作。您可以内联 sgn
.
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
if d <= Lbox/2.:
return (y < x) - (x < y)
else:
return (x < y) - (y < x)
但是 if
可以(大部分)重写为:
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
w = sgn(Lbox/2., d)
return w * sgn(x, y)
再一次,内联 sgn
,
def sgn_pbc(x, y, Lbox):
d = abs(x-y)
w = sgn(Lbox/2., d)
return w * (y < x) - (x < y)
我说主要是因为 d == Lbox/2.
这个 returns 的值是错误的。
不过还没有计时。