python - 在 python 中向上或向下舍入一半的快速方法

标签 python numpy rounding

<分区>

我有一个由复数组成的 numpy 数组,需要创建一个包含四舍五入的实部和虚部的新数组,其中四舍五入是向零或向无穷大。

在 stackoverflow 上有一些使用 decimal 包的建议,它允许指定不同类型的舍入。对于复数数组 x,以下代码有效,但速度非常慢:

    rounded_array = np.array([
        float(Decimal(x.real).quantize(0, rounding=ROUND_HALF_DOWN)) + 1j * \
        float(Decimal(x.imag).quantize(0, rounding=ROUND_HALF_DOWNs)) for x in arr])

有哪些简单但更快的替代方案? 建议使用此解决方案: How to always round up a XX.5 in numpy 但是,它仅适用于实际数组,并且比下面建议的解决方案慢得多。

最佳答案

快速就地舍入减半:

arr = arr.view(float)
m = arr % 1. <= .5
arr[m] = np.floor(arr[m])
arr[~m] = np.ceil(arr[~m])
arr = arr.view(complex)

(使用 m = arr % 1. < .5 取整)

如果您需要一个新数组而不是就地更改现有数组,请将第一行更改为 arr = arr.view(float).copy('K') .

对于 1000 个元素的数组,这比原始解决方案快大约 100 倍。


UPDATE 根据以下评论为负数:

m = arr % 1. == .5
arr[m] = np.trunc(arr[m])
arr[~m] = np.round(arr[~m])

时间

x = np.arange(-1000, 1000, .1)
arr = x + 1j * x

%%timeit
rounded_array = np.array([
        float(Decimal(x.real).quantize(0, rounding=ROUND_HALF_DOWN)) + 1j * \
        float(Decimal(x.imag).quantize(0, rounding=ROUND_HALF_DOWN)) for x in arr])
        
1.83 s ± 27.4 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

%%timeit
arr1 = arr.view(float).copy('K')
m = arr1 % 1. == .5
arr1[m] = np.trunc(arr1[m])
arr1[~m] = np.round(arr1[~m])
arr1 = arr1.view(complex)


1.78 ms ± 18.6 µs per loop (mean ± std. dev. of 7 runs, 1000 loops each)

关于python - 在 python 中向上或向下舍入一半的快速方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62651663/

相关文章:

python - 在yarn-cluster模式下运行python Spark作业

python - 如何在 debian 10 上使用 checkinstall 安装 python3.8?

Pythoncurses不接受curses.KEY_UP作为输入

c# - C# 中的 float / double Math.Round

R - 舍入到最接近的一半

python - 复杂的正则表达式在 Spacy 实体标尺中不起作用

python - 有效地填充 numpy 中的张量

python - 有效地删除 numpy 图像数组的行/列

python - 在python中更改数组的内容

c++ - 给定一个微秒值,如何准确得到一个timeval结构?/*UPDATE GETTING NEGATIVE VALUE*/