Python保存1000x1000对数正态分布矩阵到CSV为空的问题排查
问题描述
尝试生成并保存一个服从对数正态分布、尺寸为1000x1000的大型矩阵至CSV文件,但最终保存得到的文件为空,无法定位代码中的错误,相关实现代码如下:
import numpy as np import csv with open('Radius.csv', 'w') as f: shape = 1000,1000 zmin, zmax = 0.2,0.8 n = np.prod(shape) zc = np.array([]) while True: z = np.random.lognormal(mean=0.2, sigma=0.5, size=n * 100) z = z[(zmin <= z) & (z < zmax)] z = np.r_[zc, z] if len(z) >= n: break inv_r = z[:n].reshape(shape) print("1/r =",[inv_r]) writer = csv.writer(f) writer.writerows(zip(1,[inv_r]))
错误点梳理
- 循环分支逻辑颠倒:文件写入代码放在
break判断的外侧,只有当采样得到的符合区间要求的样本量不足n时才会执行写入,一旦样本量凑够1000*1000=1e6个,会直接触发break跳出循环,全程不会执行任何写入操作,这就是生成的CSV为空的核心原因。 - 样本累积逻辑失效:代码中初始定义的
zc始终是空数组,每次循环采样后都用空的zc和新采样的样本拼接,相当于每次循环都丢弃之前生成的有效样本,不仅采样效率极低,还可能触发死循环。 - 写入语法错误:
zip(1,[inv_r])写法非法,zip要求所有入参都是可迭代对象,整数1不支持迭代;就算修正该问题,直接把numpy数组对象整体作为写入项,最终CSV里只会存入数组的对象字符串,不会写入矩阵的实际数值。 - 写入器初始化位置不合理:
csv.writer放在循环内部反复重建,不符合CSV文件的写入规范,容易出现内容截断、格式错乱问题。
修正方案
修正所有逻辑问题后的可运行代码如下:
import numpy as np import csv shape = (1000, 1000) zmin, zmax = 0.2, 0.8 n = np.prod(shape) valid_samples = np.array([]) # 循环采样直到累积足够多符合区间要求的样本 while len(valid_samples) < n: raw_samples = np.random.lognormal(mean=0.2, sigma=0.5, size=n*10) filtered = raw_samples[(zmin <= raw_samples) & (raw_samples < zmax)] valid_samples = np.r_[valid_samples, filtered] # 取前n个样本重塑为目标尺寸的矩阵 inv_r = valid_samples[:n].reshape(shape) print(f"生成矩阵尺寸校验:{inv_r.shape}") # 写入CSV文件 with open('Radius.csv', 'w', newline='') as f: writer = csv.writer(f) writer.writerows(inv_r)
如果追求大矩阵的写入效率,可以跳过csv模块,直接使用numpy自带的写入方法,代码更简洁、写入速度更快:
# 替代上面csv写入的部分即可 np.savetxt('Radius.csv', inv_r, delimiter=',')
内容的提问来源于stack exchange,提问作者Wiz123
相关产品推荐
相关产品推荐

