我有一个结构化数据文件,其中包含散布着数据块的标题行。我正在将每个数据块(由标题行定义)读入单元数组的单独单元格中。例如,假设在使用textscan
加载数据后,我有一个单元格数组x
以及以下形式的标题行和EOF(headerIdx
)的索引数组:
x={'header line 1';'98.78743';'99.39717';'99.93578';'100.40125';'100.79166';'101.10525';'101.34037';'101.49553';'101.56939';'101.56072';'101.4685';'101.29184';'101.03002';'100.68249';'header line 2';'100.24887';'99.72897';'99.12274';'98.43036';'97.65215';'96.78864';'95.84054';'header line 3';'3.2';'4.31';'2.7';'4.6';'9.3'};
headerIdx=[1;16;24;30];
然后,我尝试使用sscanf
和str2mat
(由this post建议)将标题行下方的每个数据块提取到单元格数组的单独元素中。最初,这种方法失败了,因为给定数据块中的元素长度不同。这可以通过包含'%f'
参数的数字标志来解决,以帮助sscanf
知道在何处划分输入数据(如this post所示)。然后可以使用诸如以下的策略来实现结构化数据到块特定双数组的单元阵列的转换:
extract_data = @(n) sscanf(str2mat(x(headerIdx(n)+1:headerIdx(n+1)-1)).',['%' num2str(size(str2mat(x(headerIdx(n)+1:headerIdx(n+1)-1)).',1)) 'f']);
extracted_data = arrayfun(extract_data,1:numel(headerIdx)-1,'UniformOutput',false);
格式字符串的数字标志可以设置为任意大的内容以包含所有数据,或者可以在特定于块的基础上设置,如我在上面的示例中所做的那样。后一种方法导致str2mat
的冗余评估(一次输入到sscanf
,一次输入到'%f'
字符串生成器。如果不使用存储的循环语句,可以避免这种冗余临时变量中str2mat
命令的输出?注意,不能简单地将size
命令的输出应用于整个数据集上str2mat(x).'
的输出,因为标题行通常是具有最多字符数的行。
最后,我构建了上面的x
矩阵,以反映某些数据块可能与其他块具有不同精度的事实。这是以块特定方式设置格式字符串的原因。我的测试表明,尽管精确构造了块特定的格式字符串(['%' num2str(size(str2mat(x(headerIdx(n)+1:headerIdx(n+1)-1)).',1)) 'f']
),但生成的单元格数组(extracted_data
)的所有元素中的数据最终都被强制具有相同的精度(参见下面)。为什么会出现这种情况,如何纠正?
extracted_data{:}
ans =
98.7874
99.3972
99.9358
100.4013
100.7917
101.1052
101.3404
101.4955
101.5694
101.5607
101.4685
101.2918
101.0300
100.6825
ans =
100.2489
99.7290
99.1227
98.4304
97.6522
96.7886
95.8405
ans =
3.2000
4.3100
2.7000
4.6000
9.3000