【问题标题】:Load data to a numpy array by piping the output of an external program通过管道传输外部程序的输出将数据加载到 numpy 数组
【发布时间】:2016-12-23 02:28:48
【问题描述】:

我有一个程序,它输出一个巨大的 float32 数组,前面有一个 40 字节的标头。程序写入标准输出。

我可以将输出转储到一个文件中,在 python 中打开它,跳过标头的 40 个字节,然后使用 numpy.fromfile() 将其加载到 numpy 中。但是,这需要很多时间。

所以我想做的是通过读取生成它的程序的标准输出将数组直接加载到 numpy 中。但是我很难弄清楚这一点。

谢谢!

【问题讨论】:

标签: python numpy stdout


【解决方案1】:

您可以memory-map 文件而不是全部阅读。这几乎不需要时间:

np.memmap(filename, np.float32, offset=40)

当然,实际从结果中读取数据需要一些时间,但可能会通过将 I/O 与计算交错来隐藏。

如果您真的不想将数据写入磁盘,您可以使用subprocess.Popen()stdout=subprocess.PIPE 运行您的程序,并将生成的stdout 类文件对象直接传递给numpy.fromfile()

【讨论】:

    【解决方案2】:

    非常感谢所有回复/评论的人。

    我按照downshift 的建议查看了他提供的链接...

    并想出了以下内容:

    nLayers=<Number of layers in program output>
    nRows=<Number of rows in layer> 
    nCols=<Number of columns in layer>
    nBytes=<Number of bytes for each value>
    noDataValue=<Value used to code no data in program output>
    DataType=<appropriate numpy data type for values>
    
    perLayer=nRows*nCols*nBytes
    
    proc = sp.Popen(cmd+args, stdout = sp.PIPE, shell=True)
    data=bytearray()
    for i in range(0,nLayers):
       dump40=proc.stdout.read(40)
       data=data+bytearray(proc.stdout.read(perLayer))
    ndata = np.frombuffer(data, dtype=DataType)
    ndata[ndata == noDataValue]=np.nan
    ndata.shape = (nLayers,nRows,nCols)
    

    这里的关键是使用numpy.frombuffer,它使用相同的读取缓冲区来创建数组,从而避免了在内存中复制数据。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-10-13
      • 1970-01-01
      • 1970-01-01
      • 2014-04-08
      • 2012-08-03
      • 2015-10-08
      • 2019-01-30
      相关资源
      最近更新 更多