SpectralPython(SPy)的学习笔记(2)数据读取
使⽤SPy打开和访问⾼光谱图像⽂件的标准⽅法是通过图像函数,它返回⼀个SpyFile对象的实例。
SpyFile界⾯
是创建读取⾼光谱数据⽂件的对象的基类。 当创建⼀个SpyFile对象时,它提供了⼀个从相应的⽂件中读取数据的接⼝。 打开图像时,返回的实际对象将是SpyFile(BipFile,BilFile或BsqFile)的⼦类,与图像⽂件中的数据交错相对应。
让我们打开我们的⽰例图像。
In [1]: from spectral import *
In [2]: img = open_image('92AV3C.lan')
In [3]: img.__class__
Out[3]: spectral.io.bilfile.BilFile
In [4]: print img
Data Source: '/home/thomas/spectral_data/92AV3C.lan'
# Rows: 145
# Samples: 145
# Bands: 220
Interleave: BIL
Quantization: 16 bits
Data format: int16
该图像不在⼯作⽬录中,但仍处于打开状态,因为它位于SPECTRAL_DATA环境变量指定的⽬录中。 由于图像像素数据是按⾏交错的,图像函数返回了⼀个BilFile实例。
由于⾼光谱图像⽂件可能相当⼤,只有在SpyFile对象第⼀次创建时才从⽂件中读取元数据。 图像数据值只有在通过SpyFile⽅法特别要求时才能读取。 SpyFile类提供了⼀个下标运算符,其⾏为与numpy数组下标运算符⾮常相似。 SpyFile对象被下标为MxNxB数组,其中M 是图像中的⾏数,N是列数,B是带的数量。
In [5]: img.shape
Out[5]: (145, 145, 220)
In [6]: pixel = img[50,100]
In [7]: pixel.shape
Out[7]: (220,)
rows函数的使用方法及实例In [8]: band6 = img[:,:,5]
In [9]: band6.shape
Out[9]: (145, 145, 1)
在执⾏下标运算符调⽤之前,不从⽂件中读取图像数据值。 请注意,由于Python索引从0开始,因此img [50,100]指的是图像的第51⾏和第101列的像素。 同样的,img [:,:,5]是指图像第6条带的所有⾏和列。
为特定图像⽂件返回的SpyFile⼦类实例也将提供以下⽅法
SpyFile对象有⼀个band成员,它是⼀个BandInfo对象的实例,它包含有关图像光谱波段的可选信息。
加载整个图像
需要注意的是,图像数据被SpyFile对象按需读取,并且数据不被缓存。每次调⽤SpyFile下标操作符或其中⼀个SpyFile读取⽅法时,都会从相应的图像数据⽂件中读取数据,⽽不管之前是否读取过相同的数据。这样做是为了避免在处理⾮常⼤的图像⽂件时消耗太多内存。 当执⾏只需要读取⼤图像中的⼀⼩部分数据(例如,读取RGB带以显⽰图像)的操作时,它也提⾼了性能。按需读取数据⽽不缓存数据的缺点是,运⾏需要访问所有数据的算法时可能会产⽣严重的运⾏时间损失。 如果算法需要对数据进⾏迭代访问,性能会更差。
为了提⾼光谱算法的性能,最好使⽤load⽅法将整个图像加载到内存中,该⽅法返回⼀个ImageArray对象。ImageArray提供了完整的numpy.ndarray接⼝,以及SpyFile接⼝ 。
In [1]: arr = img.load()
In [2]: arr.__class__
Out[2]: spectral.spectral.ImageArray
In [3]: print arr.info()
# Rows: 145
# Samples: 145
# Bands: 220
Data format: float32
In [4]: arr.shape
Out[4]: (145, 145, 220)
由于SPy主要设计⽤于在光谱范围内进⾏处理,因此⽆论源图像数据⽂件的交错如何,内存中的spectral.ImageArray对象都将始终按像素交织数据。换句话说,numpy.ndarray形状将是(numRows,numCols,numBands)。 ImageArray对象始终包含32位浮点数
注意:
在调⽤load⽅法之前,重要的是要考虑⽣成的ImageArray对象将要消耗的内存量。由于spectral.ImageArray使⽤32位浮点值,因此消耗的内存量⼤约为4 * numRows * numCols * numBands个字节
NumPy memmap Interface
作为将整个图像加载到内存中的⼀种替代⽅法,访问图像数据的速度稍慢(但更具有内存效率)是使⽤numpy memmap对象,由SpyFile 对象的open_memmap⽅法返回。也可以使⽤memmap对象将⽇期写⼊图像⽂件。
⽂件格式⽀持
ENVI头⽂件
ENVI [1]是⼀个流⾏的商业软件包,⽤于处理和分析地理空间图像。 SPy可以读取具有相关ENVI头⽂件的图像,并可以使⽤ENVI头读取和写⼊光谱库。ENVI⽂件由SPy图像功能⾃动打开,但图像也可以作为ENVI⽂件显式打开。 如果数据⽂件位于标题的单独⽬录中,或者数据⽂件具有SPy⽆法识别的异常⽂件扩展名,则可能需要明确打开ENVI⽂件。
In [5]: import vi as envi
In [6]: img = envi.open('cup95eff.int.hdr', 'cup95eff.int')
In [7]: import vi as envi
In [8]: lib = envi.open('spectra.hdr')
In [9]: lib.names[:5]
Out[9]:
[u'construction asphalt',
u'construction concrete',
u'red smooth-faced brick',
u'weathered red brick',
u'bare red brick']
另请参见将图像数据写⼊⽂件的功能:
在磁盘上创建⼀个分配有存储空间的新映像⽂件。
:将现有的图像或ndarray保存到具有ENVI标头的⽂件中。
AVIRIS数据
SPy⽀持由机载可视/红外成像光谱仪(AVIRIS)⽣成的数据⽂件[2]。AVIRIS⽂件由open_image函数⾃动识别; 但是,光谱波段校准⽂件不能被⾃动识别; 因此您可能需要将图像作为AVIRIS⽂件显式打开并指定cal⽂件。
In [10]: img = aviris.open('f970619t01p02_r02_sc01.a.rfl', 'f970619t01p02_r02.a.spc')
您也可以单独加载波段校准⽂件(如果波段校准⽂件是AVIRIS格式,但图像不是这样,则可能需要这样
做)。
In [11]: img = open_image('92AV3C.lan')
In [12]: img.bands = ad_aviris_bands('92AV3C.spc')
ERDAS/Lan数据
ERDAS / Lan⽂件格式是由图像⾃动识别的。 ⼀个⽂件不太可能需要作为⼀个Lan⽂件明确打开,但可以按如下⽅式完成。
In [13]: import das as erdas
In [14]: img = erdas.open('92AV3C.lan')
参考⽂献
ENVI is a registered trademark of Exelis Visual Information Solutions.
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论