How to search a field in a structure and extract all fields that match

374 ビュー (過去 30 日間)
Dave
Dave 2017 年 3 月 24 日
回答済み: George Abrahams 2022 年 12 月 30 日
Hopefully I'll explain clearly as I haven't worked with structures much. I have been given a large 1x1 structure of arrays with numerous fields. I want to search one field to match a specific string. I then want to extract from the structure all fields for those cases where the string matched. I would prefer to do this with out loops. For an array of structures, I've been able to use logical indexing to access and extract data using "index2 = cellfun(@(x) any(strcmp(x, test)), {diab2.preg})" and then just index into the structure, but this doesn't work for a structure of arrays.

採用された回答

Sindhu Priya
Sindhu Priya 2017 年 3 月 28 日
Hi Dave,
I think, the following code snippet will help you.
s.f1= {'Sunday' 'Monday'}
s.f2= {'Sunday' 'Monday' 'Tuesday'}
s.f3= 'Tuesday'
s.f4= 'Wednesday'
s.f5= 'Thursday'
s.f6: 'Friday'
s.f7: 'Saturday'
index2 = structfun(@(x) any(strcmp(x, 'Monday')),s)
and the generated Output is
index2 =
7×1 logical array
1
1
0
0
0
0
0
Please refer this link for more details about 'structfun'.
Regards,
Sindhu
  1 件のコメント
Dave
Dave 2017 年 4 月 1 日
編集済み: Dave 2017 年 4 月 2 日
Thanks Sindhu, from this and continuing to research structures I realize the data I'm given is a structure of arrays. As an example the structure data is made up of
data.Sen = {'U1'; 'U2'; 'U1'; 'U1'}
data.Tid = {'1'; '1'; '1';'2'}
data.Obj = {'U1_1';'U2_1';'U1_2';U1_1'}
data.X = {'10'; '5'; '3'; '1'}
data.Y = {'20'; '7'; '4'; '2'}
I've sort of brute forced a way to get the related data I want with
senidx = strcmp(data.Sen,'U1');
thesen = data.Sen(senidx)
theX = data.X(senidx)
theY = data.Y(senidx)
theTid = data.TID(senidx)
but I expect there is a more elegant way to do this.
I thought the following would work
for nField = 1:numel(myfieldnames)
mField = myfieldnames{nField}
mydata.(mField) = data.(mField)(strcmp(data.Sen_T,'U1'))
end
but I get this error: Struct contents reference from a non-struct array object.
I think I'm close so any further insight would be appreciated.

サインインしてコメントする。

その他の回答 (1 件)

George Abrahams
George Abrahams 2022 年 12 月 30 日
Old question, but for future reference, most likely you wanted to use a table, not a structure of cell arrays, as this makes it easy.
data.Sen = { 'U1'; 'U2'; 'U1'; 'U1' };
data.Tid = { '1'; '1'; '1'; '2' };
data.Obj = { 'U1_1'; 'U2_1'; 'U1_2'; 'U1_1' };
data.X = { '10'; '5'; '3'; '1' };
data.Y = { '20'; '7'; '4'; '2' };
% Convert structure of cell arrays to table (fields become columns).
data = struct2table( data );
% Find logical indices of the matching table rows.
% If you don't care about case or additional letters, see: strncmp,
% strcmpi, strncmpi.
rows = strcmp( data.Sen, 'U1' );
% Extract these rows from the table.
data( rows, : )
% ans = 3×5 table
% Sen Tid Obj X Y
% {'U1'} {'1'} {'U1_1'} {'10'} {'20'}
% {'U1'} {'1'} {'U1_2'} {'3' } {'4' }
% {'U1'} {'2'} {'U1_1'} {'1' } {'2' }
If you didn't want to do that for some reason, you could use my fieldfun function on File Exchange / GitHub, which process the fields of one or more structures and outputs a structure with the same fields.
idx = strcmp( data.Sen, 'U1' );
fieldfun( @(x) x(idx)', data )
% ans = struct with fields:
% Sen: {'U1' 'U1' 'U1'}
% Tid: {'1' '1' '2'}
% Obj: {'U1_1' 'U1_2' 'U1_1'}
% X: {'10' '3' '1'}
% Y: {'20' '4' '2'}

カテゴリ

Help Center および File ExchangeStructures についてさらに検索

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by