Перебора структура поля в MATLAB
мой вопрос легко резюмируется как:"почему следующее не работает?"
teststruct = struct('a',3,'b',5,'c',9)
fields = fieldnames(teststruct)
for i=1:numel(fields)
fields(i)
teststruct.(fields(i))
end
выход:
ans = 'a'
??? Argument to dynamic structure reference must evaluate to a valid field name.
тем более что teststruct.('a')тут работа. И fields(i) выводит ans = 'a'.
Я не могу заставить себя думать об этом.
4 ответов:
вы должны использовать фигурные скобки (
{}) кfieldsСfieldnamesфункция возвращает a ячейки массива строк:for i = 1:numel(fields) teststruct.(fields{i}) endиспользование скобок для доступ к данным в ячейке массива просто вернет другой массив ячеек, который отображается иначе, чем массив символов:
>> fields(1) % Get the first cell of the cell array ans = 'a' % This is how the 1-element cell array is displayed >> fields{1} % Get the contents of the first cell of the cell array ans = a % This is how the single character is displayed
С
fieldsилиfnsявляются массивы ячеек, вы должны индексировать с фигурными скобками{}для доступа к содержимому ячейки, т. е. строки.обратите внимание, что вместо циклического перебора числа, вы также можете перебирать
fieldsнепосредственно, используя аккуратные функции Matlab, которые позволяют вам перебирать любой массив. Переменная итерации принимает значение каждого столбца массива.teststruct = struct('a',3,'b',5,'c',9) fields = fieldnames(teststruct) for fn=fields' fn %# since fn is a 1-by-1 cell array, you still need to index into it, unfortunately teststruct.(fn{1}) end
ваш fns-это массив cellstr. Вам нужно индексировать его с помощью {} вместо (), чтобы получить одну строку как символ.
fns{i} teststruct.(fns{i})индексирование в него с помощью () возвращает массив cellstr длиной 1, который не имеет того же формата, что и массив char, который ".(имя)" динамическая ссылка на поле хочет. Форматирование, особенно в выводе на дисплей, может быть запутанным. Чтобы увидеть разницу, попробуйте это.
name_as_char = 'a' name_as_cellstr = {'a'}
вы можете использовать для каждого набора инструментов из http://www.mathworks.com/matlabcentral/fileexchange/48729-for-each.
>> signal signal = sin: {{1x1x25 cell} {1x1x25 cell}} cos: {{1x1x25 cell} {1x1x25 cell}} >> each(fieldnames(signal)) ans = CellIterator with properties: NumberOfIterations: 2.0000e+000использование:
for bridge = each(fieldnames(signal)) signal.(bridge) = rand(10); endмне очень нравится. Кредит, конечно, достанется Джереми Хьюзу, который разработал инструментарий.
Comments