python - 如何在 python 中打开 .ProcSpec 文件?
问题描述
我有从 SpectraSuite 软件(已处理光谱,OOI 二进制文件)获得的数据,我尝试使用
f = open(r'C:\Users\path/file.ProcSpec', 'rb')
file_content = f.read()
f.close()
但 file_content 是类似“b'PK\x03\x04\x14\x00\x08\x00\x08\x007t\x...”的数据。如何将这种类型的文件作为表格数据打开?
解决方案
方法一
在 Spectra Suite 中,您可以再次打开并导出它们,同时将文件类型设置为Tab Delimited
. 然后您应该能够使用 csv lib 导入它们。
在此处查看如何打开 csv 文件。
直接从 Python
这是一个 Matlab 代码,它可以满足您的需求。
从 Matlab 代码中,我们看到 OOI 格式是一个压缩的 xml。此外,似乎有些字符无法被 XML 解析器解析。
知道了这一点,可以使用以下代码打开文件。请注意,这是一种无需错误处理或彻底测试的快速实现。
import os
import shutil
import glob
import xml.etree.ElementTree as ET
import numpy as np
def parseNodeText(node):
# bool
nodeText = node.text
if 'true' == nodeText or 'false' == nodeText:
return nodeText == 'true'
# int
try:
return int(nodeText)
except:
pass
# float
try:
return float(nodeText)
except:
pass
# text
return nodeText
def extractArrayFromNode(node):
arr = []
for val in node:
arr.append(parseNodeText(val))
if 'double' in node[0].tag:
dt = np.float32
elif 'int' in node[0].tag:
dt = np.int32
else:
dt = np.float32
return np.array(arr,dtype=dt)
def readProcSpecFile(filePath):
dirName = os.path.dirname(filePath)
tmpdir = os.path.join(dirName,'tmp')
os.makedirs(tmpdir, exist_ok=True)
tmpFile= os.path.join(tmpdir,'tmp.zip')
shutil.copy(filePath, tmpFile)
shutil.unpack_archive(tmpFile, tmpdir)
for f in glob.glob(tmpdir+r'\*.xml'):
if 'OOISignatures.xml' in f:
continue
with open(f,"rb") as fi:
s = fi.read()
badChars = [b'\xa0',b'\x89',b'\x80']
for c in badChars:
s = s.replace(c,b' ')
with open(f,"wb") as fi:
fi.write(s)
tree = ET.parse(f.encode("utf-8"))
root = tree.getroot()
result = []
for spectra in root[0]:
s = spectra[0]
spect = {}
for node in spectra:
t = node.tag
n = parseNodeText(node)
if t == 'pixelValues':
spect[t] = extractArrayFromNode(node)
elif t == 'channelWavelengths':
spect[t] = extractArrayFromNode(node)
elif t == 'acquisitionTime':
times = {}
for val in node:
times[val.tag] = parseNodeText(val)
spect[t] = times
elif t == 'certificates':
pass
elif t == 'channelCoefficients':
pass
else:
spect[t] = n
result.append(spect)
shutil.rmtree(tmpdir)
return result
下面是一个关于如何使用它的例子:
iFile = r'your\path\file.ProcSpec'
spects = readProcSpecFile(iFile)
spect = spects[0]
print(spect.keys())
wavelength = spect['channelWavelengths']
pixelValues = spect['pixelValues']
这是输出:
dict_keys(['saturated', 'integrationTime', 'strobeEnabled', 'strobeDelay', 'pixelValues', 'acquisitionTime', 'boxcarWidth', 'scansToAverage', 'correctForElectricalDark', 'correctForNonLinearity', 'correctForStrayLight', 'rotationEnabled', 'userName', 'channelWavelengths', 'channelNumber', 'channelStabilityScanEnabled', 'channelExternalTriggerEnabled', 'laserWavelength', 'interlock', 'numberOfPixels', 'numberOfDarkPixels', 'spectrometerSerialNumber', 'spectrometerFirmwareVersion', 'spectrometerClass', 'spectrometerPlugins', 'spectrometerNumberOfChannels', 'spectrometerMaximumIntensity', 'spectrometerMinimumIntegrationTime', 'spectrometerMaximumIntegrationTime', 'spectrometerIntegrationTimeStep', 'spectrometerIntegrationTimeBase', 'spectrometerNumberOfPixels', 'spectrometerNumberOfDarkPixels'])
In [2]:wavelength
Out[2]:array([ 199.51251, 199.98462, 200.4567 , ..., 1116.266 , 1116.6813 ,
1117.0964 ], dtype=float32)
In [3]:pixelValues
Out[3]:array([64000. , 1958.1, 1958.1, ..., 1957.1, 1957.1, 1957.5],
dtype=float32)
这是wavelength
和values
数组的图:
推荐阅读
- javascript - Json 对象到对象
- kotlin - 由于 jsNpm 配置,KMP 库 gradle allTests 失败
- r - summarise() 使用 dplyr 的案例子集
- angular8 - 页面刷新时丢失绑定数组
- postgresql - xpath(未知,字符不同)不存在
- react-native - React Native 远程 JSON 配置文件 react native
- bokeh - 我可以在 Bokeh HoverTool 文本中添加一个很酷的 Unicode 上/下三角形吗?
- html - 我该如何停止
- 重叠的元素
- python - 如何在 GeoPandas 的图例中显示两个颜色图
- r - 如何在分组数据框中创建一列百分比?