这是
的后续问题Reading parameters from a text file into the workspace
我想知道,我将如何阅读以下内容:
% ---------------------- details --------------------------
%---------------------------------------------------------------
% location:
lat = 54.35
lon = -2.9833
%
Eitan T建议使用:
fid = fopen(filename);
C = textscan(fid, '%[^= ]%*[= ]%f', 'CommentStyle', '%')
fclose(fid);
从文件中获取信息然后
lat = C{2}(strcmp(C{1}, 'lat'));
lon = C{2}(strcmp(C{1}, 'lon'));
获取相关参数。我怎么能改变这一点来阅读以下内容:
% ---------------------- details --------------------------
%---------------------------------------------------------------
% location:
lat = 54.35
lon = -2.9833
heights = 0, 2, 4, 7, 10, 13, 16, 19, 22, 25, 30, 35
Volume = 6197333, 5630000, 4958800, 4419400, 3880000, 3340600,
3146800, 2780200, 2413600, 2177000, 1696000, 811000
%
其中变量应包含等号后的所有数据点(直到下一个变量的开始,在这种情况下为Volume)?
感谢您的帮助
答案 0 :(得分:2)
这是一种方法,它使用一些肮脏的字符串黑客和eval
来获得结果。这适用于您的示例,但我不会真的推荐它:
fid = fopen('data.txt');
contents = textscan(fid, '%s', 'CommentStyle', '%', 'Delimiter', '\n');
contents = contents{1};
for ii = 1:length(contents)
line = contents{ii};
eval( [strrep(line, '=', '=['), '];'] ) # convert to valid Matlab syntax
end
更好的方法是使用textscan
for ii = 1:length(contents)
idx = strfind(contents{ii}, ' = ');
vars{ii} = contents{ii}(1:idx-1);
vals(ii) = textscan(contents{ii}(idx+3:end), '%f', 'Delimiter', ',');
end
现在,变量vars
和vals
包含变量的名称及其值。要提取值,您可以执行类似
ix = strmatch('lat', vars, 'exact');
lat = vals{ix};
ix = strmatch('lon', vars, 'exact');
lon = vals{ix};
ix = strmatch('heights', vars, 'exact');
heights = vals{ix};
ix = strmatch('Volume', vars, 'exact');
volume = vals{ix};
答案 1 :(得分:1)
这可以通过两步法实现:
但这里有一点点缺点;你的行似乎遵循两种格式;一个是步骤1)中描述的那个,另一个是前一行的继续,其包含数字。
因此,需要额外的步骤:
我认为这会解决问题:
fid = fopen('data.txt');
C = [];
try
while ~feof(fid)
% Read next set of data, assuming the "first format"
C_new = textscan(fid, '%[^= ]%*[= ]%s', 'CommentStyle', '%', 'Delimiter', '');
C = [C; C_new]; %#ok
% When we have non-trivial data, check for the "second format"
if ~all(cellfun('isempty', C_new))
% Second format detected!
if ~feof(fid)
% get the line manually
D = fgetl(fid);
% Insert new data from fgetl
C{2}(end) = {[C{2}{end} C{1}{end} D]};
% Correct the cell
C{1}(end) = [];
end
else
% empty means we've reached the end
C = C(1:end-1,:);
end
end
fclose(fid);
catch ME
% Just to make sure to not have any file handles lingering about
fclose(fid);
throw(ME);
end
% convert second elements to floats
C{2} = cellfun(@str2num, C{2}, 'UniformOutput', false);
答案 2 :(得分:0)
如果你可以摆脱多行音量线,你所写的是有效的matlab。因此,只需使用run命令将参数文件作为matlab脚本调用。
run(scriptName)
正如其他人所表明的那样,你唯一的另一种选择是写出最终看起来像一个混蛋的Matlab解析器。肯定有更好的方式来度过你的时间而不是那样做!