stackoverflow上有一个答复,可以帮助找到0x41c不能使用时的偏移:
I know this thread is a bit old now, but I needed to read SPA files recently, and would like to share how I managed to cope with them.
As stated by cooooldog, 0x41c offset is not standard.
However, this offset is coded in the spa file itself.
When editing a spa file, there is a short header at the beginning, then many zeros.
From 0x11e are non-zero values. Here is how I managed to find the correct offset for my spectral files:
Starting from 0x11e, I start reading int32 values.
It appears that the data offset is coded just before this value : 54 18 00 00 (which is 6228 in decimal).
So by looking for 6228, the offset needed to find data later in the file is the integer found just before this value of 6228.
If you continue editing your spa file, you should find floating point values, 32-bit coded, placed just after a bunch of text.
From now, reading those values is possible, by just replacing 0x41c by the address found.
If this may help anyone...
function address = getStart(filename)
try
% Open the file
fid=fopen(filename,'r');
% Jump where the values become interesting
fseek(fid,hex2dec('11e'),'bof');
% Pattern we're looking for
pattern = 6228;
suspect = 0;
while suspect~=pattern
oldSuspect = suspect;
suspect = fread(fid,1,'int32');
end
% The correct address is just before our current suspect
address = oldSuspect;
% Close the file
fclose(fid);
catch ex
address = 0;
disp(ex)
end
http://stackoverflow.com/questions/2887151/how-to-read-data-from-a-nicolet-ftir-spectral-file-with-extension-of-spa
时间是, 2010年5月23日 16:08分, 星期天
用了两天时间, 这次主要是借助工具自己破解的.
上次搞Perkin Elmer的 *.sp 是借助了现成的matlab代码变成VBA的
哈哈
现在存在的问题主要是, 读取谱图时候的偏移量, 对于不同的*.spa谱图文件而言, 并不是一个固定值
比如, 三个谱图中, 就有两个不同的偏移量,
0x488h, 0x41ch
这说明, 跳转的过程中, 利用了某种逻辑规则, 让人稍微有些郁闷...
0x41ch是文件没有做过修改的原始谱图的偏移量
0x488h则不是一个固定的偏移, 是文件被修改之后, 修改的信息添加在谱图数据之前, 导致偏移量增加
因此, 只需考虑0x41c h的偏移就可以了
代码如下:
clc
filename='c:/Documents and Settings/User Name/My Documents/Spectral File.SPA';
fid=fopen(filename,'r');
% Find the points number
fseek(fid,hex2dec('234'),'bof');
Number_of_DataPoints=fread(fid,1,'int32');
%Find the maximum and minimum of Wavenumber (cm-1) range
fseek(fid,576,'bof');
Maximum_Wavenumber=fread(fid,1,'single');
Minimum_Wavenumber=fread(fid,1,'single');
Interval=(Maximum_Wavenumber-Minimum_Wavenumber)/(Number_of_DataPoints-1);
Wavenumber=linspace(Minimum_Wavenumber,Maximum_Wavenumber,Number_of_DataPoints).';
Wavenumber=flipud(Wavenumber);
%Find the Y-Axis data type: %Transmittance or Absorbance
fseek(fid,hex2dec('360'),'bof'); Y_Label=char(fread(fid,14,'uchar')');
% How to define the offset for spectral data still remains unresolved.
fseek(fid,hex2dec('41c'),'bof');
spectrum=fread(fid,Number_of_DataPoints,'single');%'double'); % float64, %real*8
figure(1),plot(Wavenumber,spectrum,'r'); set(gcf,'color','w');
set(gca,'xdir','rev','xcolor','b','ycolor','b','xlim',[round(Minimum_Wavenumber),round(Maximum_Wavenumber)]);
xlabel('Wavenumber /cm^{-1}'); ylabel(Y_Label);
如果0x41ch不行,可以参考stackoverflow上的方法
|
I know this thread is a bit old now, but I needed to read SPA files recently, and would like to share how I managed to cope with them. As stated by cooooldog, 0x41c offset is not standard. However, this offset is coded in the spa file itself. When editing a spa file, there is a short header at the beginning, then many zeros. From 0x11e are non-zero values. Here is how I managed to find the correct offset for my spectral files: Starting from 0x11e, I start reading int32 values. It appears that the data offset is coded just before this value : 54 18 00 00 (which is 6228 in decimal). Edit : I've received new set of spa files where the searched pattern is no longer 54 18 00 00 but 40 61 00 00 (24896), so this might not be standard as well. In fact it appears that starting address is either coded at 172h or 182h in the spa file. I do still need a way to find it out. So by looking for 6228, the offset needed to find data later in the file is the integer found just before this value of 6228. If you continue editing your spa file, you should find floating point values, 32-bit coded, placed just after a bunch of text. From now, reading those values is possible, by just replacing 0x41c by the address found. If this may help anyone...
function address = getStart(filename)
try
% Open the file
fid=fopen(filename,'r');
% Jump where the values become interesting
fseek(fid,hex2dec('11e'),'bof');
% Pattern we're looking for
pattern = 6228;
suspect = 0;
while suspect~=pattern
oldSuspect = suspect;
suspect = fread(fid,1,'int32');
end
% The correct address is just before our current suspect
address = oldSuspect;
% Close the file
fclose(fid);
catch ex
address = 0;
disp(ex)
end
|
|
|
|
I found where the spectral offset is set, it is on position 386:
fseek(fid,386,'bof');
spectral_offset = fread(fid,1,'int32')
fseek(fid,spectral_offset,'bof');
spectrum=fread(fid,Number_of_DataPoints,'single');
|
|
answered
Oct 20 '15 at 13:05
| |
|
|