将 numpy 数组转换为 CSV 字符串,将 CSV 字符串转换回 numpy 数组
Posted
技术标签:
【中文标题】将 numpy 数组转换为 CSV 字符串,将 CSV 字符串转换回 numpy 数组【英文标题】:Convert a numpy array to a CSV string and a CSV string back to a numpy array 【发布时间】:2013-05-05 04:12:52 【问题描述】:我必须将一个 numpy 浮点数组转换为一个字符串(以存储在 SQL DB 中),然后还将相同的字符串转换回一个 numpy 浮点数组。
这就是我要去字符串的方式 (based on this article)
VIstring = ''.join(['%.5f,' % num for num in VI])
VIstring= VIstring[:-1] #Get rid of the last comma
所以首先这确实有效,这是一个好方法吗?他们是摆脱最后一个逗号的更好方法吗?或者我可以使用join
方法为我插入逗号吗?
其次,更重要的是,有没有一种巧妙的方法可以从字符串返回到浮点数组?
这里是数组和字符串的例子:
VI
array([ 17.95024446, 17.51670904, 17.08894626, 16.66695611,
16.25073861, 15.84029374, 15.4356215 , 15.0367219 ,
14.64359494, 14.25624062, 13.87465893, 13.49884988,
13.12881346, 12.76454968, 12.40605854, 12.00293814,
11.96379322, 11.96272486, 11.96142533, 11.96010489,
11.95881595, 12.26924591, 12.67548634, 13.08158864,
13.4877041 , 13.87701221, 14.40238245, 14.94943786,
15.49364166, 16.03681428, 16.5498035 , 16.78362298,
16.90331119, 17.02299387, 17.12193689, 17.09448654,
17.00066063, 16.9300633 , 16.97229868, 17.2169709 , 17.75368411])
VIstring
'17.95024,17.51671,17.08895,16.66696,16.25074,15.84029,15.43562,15.03672,14.64359,14.25624,13.87466,13.49885,13.12881,12.76455,12.40606,12.00294,11.96379,11.96272,11.96143,11.96010,11.95882,12.26925,12.67549,13.08159,13.48770,13.87701,14.40238,14.94944,15.49364,16.03681,16.54980,16.78362,16.90331,17.02299,17.12194,17.09449,17.00066,16.93006,16.97230,17.21697,17.75368'
哦,是的,%.5f
的精度损失完全没问题,这些值由原始点插值,只有小数点后 4 位精度,所以我不需要打败它。所以在恢复 numpy 数组时,我很高兴只得到 5 位小数精度(显然我想)
【问题讨论】:
您可以查看 numpy savetxt 和 loadtxt 函数 @MattAnderson 有没有办法使用这些方法将文本直接放入字符串中,然后直接从内存中的字符串中加载而不是使用文件? 【参考方案1】:>>> import numpy as np
>>> from cStringIO import StringIO
>>> VI = np.array([ 17.95024446, 17.51670904, 17.08894626, 16.66695611,
16.25073861, 15.84029374, 15.4356215 , 15.0367219 ,
14.64359494, 14.25624062, 13.87465893, 13.49884988,
13.12881346, 12.76454968, 12.40605854, 12.00293814,
11.96379322, 11.96272486, 11.96142533, 11.96010489,
11.95881595, 12.26924591, 12.67548634, 13.08158864,
13.4877041 , 13.87701221, 14.40238245, 14.94943786,
15.49364166, 16.03681428, 16.5498035 , 16.78362298,
16.90331119, 17.02299387, 17.12193689, 17.09448654,
17.00066063, 16.9300633 , 16.97229868, 17.2169709 , 17.75368411])
>>> s = StringIO()
>>> np.savetxt(s, VI, fmt='%.5f', newline=",")
>>> s.getvalue()
'17.95024,17.51671,17.08895,16.66696,16.25074,15.84029,15.43562,15.03672,14.64359,14.25624,13.87466,13.49885,13.12881,12.76455,12.40606,12.00294,11.96379,11.96272,11.96143,11.96010,11.95882,12.26925,12.67549,13.08159,13.48770,13.87701,14.40238,14.94944,15.49364,16.03681,16.54980,16.78362,16.90331,17.02299,17.12194,17.09449,17.00066,16.93006,16.97230,17.21697,17.75368,'
>>> np.fromstring(s.getvalue(), sep=',')
array([ 17.95024, 17.51671, 17.08895, 16.66696, 16.25074, 15.84029,
15.43562, 15.03672, 14.64359, 14.25624, 13.87466, 13.49885,
13.12881, 12.76455, 12.40606, 12.00294, 11.96379, 11.96272,
11.96143, 11.9601 , 11.95882, 12.26925, 12.67549, 13.08159,
13.4877 , 13.87701, 14.40238, 14.94944, 15.49364, 16.03681,
16.5498 , 16.78362, 16.90331, 17.02299, 17.12194, 17.09449,
17.00066, 16.93006, 16.9723 , 17.21697, 17.75368])
【讨论】:
啊,将字符串设置为文件缓冲区...要走的路。知道那里应该有一些聪明的方法 这与我发布的链接中的方法 5 非常相似,我想我应该已经注意到了。谢谢。我可能会坚持 Boud 的方法 @Dan 不是真的,因为我的代码中的所有操作都是在C
级别执行的,所以它可能会更快,而且它还避免了使用 numpy
函数重新发明***。跨度>
【参考方案2】:
如果你想要一些字符串表示(不一定是 CSV),你可以试试这个,我一直在使用:
import numpy, json
## arr is some numpy.ndarray
s = json.dumps(arr.tolist())
arrback = numpy.array(json.loads(s))
它适用于大多数常见的数据类型。
【讨论】:
+1 这很酷,特别是如果您需要保持精度。【参考方案3】:首先你应该这样使用join
来避免最后一个逗号问题:
VIstring = ','.join(['%.5f' % num for num in VI])
然后读取它,使用numpy.fromstring
:
np.fromstring(VIstring, sep=',')
【讨论】:
非常好的功能建议@Boud. 不客气@Pramit:pandas 足够强大,它会让用户忘记底层的 numpy 功能以上是关于将 numpy 数组转换为 CSV 字符串,将 CSV 字符串转换回 numpy 数组的主要内容,如果未能解决你的问题,请参考以下文章
将 numpy 数组转换为 pyspark 中的 DataFrame 以导出为 csv
为啥将 numpy 数组转换为 csv 文件不显示属性名称,而是将第一行值作为属性名称?