如何实现保持元素总和不变的NumPy数组重采样/尺寸调整?
实现方案
NumPy 没有内置专门适配该需求的现成函数,但可以通过简单的自定义函数实现,完全匹配「缩放后数组总和不变」的同总时长采样率对齐场景。
通用函数代码(适配整数倍缩放,符合你给出的场景)
import numpy as np def scale_array_preserve_sum(arr, target_length): original_length = len(arr) # 校验是否为整数倍缩放,同总时长的不同采样率必然满足该条件 assert original_length % target_length == 0 or target_length % original_length == 0, "仅支持整数倍缩放场景" if target_length < original_length: # 降采样:按分组求和,保持总和不变 group_size = original_length // target_length return arr.reshape(target_length, group_size).sum(axis=1) else: # 上采样:每个值平均拆分到多个采样点,保持总和不变 repeat_times = target_length // original_length return np.repeat(arr, repeat_times) / repeat_times
效果验证
和你给出的示例预期完全一致:
# 示例1:将4采样点的array1缩放到2采样点 array1 = np.array([4, 4, 4, 4]) scaled_array1 = scale_array_preserve_sum(array1, 2) print(scaled_array1) # 输出 [8 8] array2 = np.array([5, 5]) print(scaled_array1 + array2) # 输出 [13 13] # 示例2:将2采样点的array2缩放到4采样点 scaled_array2 = scale_array_preserve_sum(array2, 4) print(scaled_array2) # 输出 [2.5 2.5 2.5 2.5] print(array1 + scaled_array2) # 输出 [6.5 6.5 6.5 6.5]
非整数倍缩放扩展(可选)
如果需要适配非整数倍的缩放场景,可以先对数组做普通插值缩放到目标长度,再做总和校正即可:
def scale_array_preserve_sum_non_integer(arr, target_length): original_sum = arr.sum() # 先使用线性插值缩放到目标长度 scaled_arr = np.interp( np.linspace(0, len(arr)-1, target_length), np.arange(len(arr)), arr ) # 校正总和 return scaled_arr * (original_sum / scaled_arr.sum())
内容的提问来源于stack exchange,提问作者Ken
相关产品推荐
相关产品推荐

