2016-09-29 3 views
0

特定のフィールドを持つ構造体配列があります。今私は、特定のフィールドが空であるすべての行をフィルタリングしたいと思います。特定のフィールドが空の場合に構造体配列からデータをフィルタリングする方法

基本的に私が今持っているものは次のとおりです。

data(1).elem1 = 1; 
data(1).elem2 = 2; 
data(1).elem3 = 3; 
data(2).elem1 = 4; 
data(2).elem3 = 6; 
data(3).elem1 = 7; 
data(3).elem2 = 8; 
data(4).elem1 = 9; 
data(4).elem2 = 10; 
data(4).elem3 = 11; 
data(5).elem1 = 9; 
data(5).elem3 = 11; 

data 

fields = {'elem2,elem3'}; 

data(any(~cellfun(@(x) any(~isempty(x)), {data.('elem2'); data.('elem3')}))) = []; 

これは大丈夫動作します。しかし、具体的には{data.('elem2'); data.('elem3')}を表現したくありません。単純に変数fieldsを使用したいと思います。

フィールドをループして{data.('elem2'); data.('elem3')}を含む一時変数を作成することができます。しかし、私はこれをしないことを好む。私はもっ​​と巧妙な方法があると思うので、私が現在行っているように、それがより効率的に行えないのだろうかと思います。

+0

「フィールド」の定義に間違いがあります。 'fields = {'elem2'、 'elem3'};'でなければなりません。そして、あなたは 'data(fields {2})})))= [];'(あなたが持っている ' 1つの余分な 'any'と2つの追加否定!) – erfan

答えて

2

構造体をセルに変換し、cellfunを使用して、の空白値があるかどうかを確認することができます。フィールド。次に、ismemberを使用して、チェックするフィールドのインデックスを探します。

fields = {'elem2','elem3'}; 
emptyIdx = squeeze(cellfun('isempty', struct2cell(data))); 
idxToRemove = any(emptyIdx(ismember(fieldnames(data), fields),:), 1); 

例:

data(1).elem1 = 1; 
data(1).elem2 = 2; 
data(1).elem3 = 3; 
data(2).elem1 = 4; 
data(2).elem3 = 6; 
data(3).elem1 = 7; 
data(3).elem2 = 8; 
data(4).elem1 = 2; 
data(4).elem3 = 5; 
data(4).elem2 = 4; 

はインデックスのみ1と4

data = 
1x2 struct array with fields: 
    elem1 
    elem2 
    elem3 
+0

私はコードの一部を使うことができると思うが、コードは私が望むように機能しないので、サンプルデータセットでテストしようとする。要素を削除しません。 –

+0

コードは、実際には 'data'の要素にないフィールドでフィルタリングします。追加したデータセットでコードを試してください。要素の数がフィールドの数と等しいために機能した理由。 –

+1

@ WG-真、混合行と列。私の解決策を 'squeeze'で更新しました – NLindros

0

とデータ構造体を与えるここでのインデックスを検索

I=ismember(fieldnames(data), {'elem2', 'elem3'}); 
data(~arrayfun(@(x) any(I & structfun(@isempty, x)), data))=[]; 

それを行うための一つの方法であります関心のある分野を使用してdataのすべての要素を繰り返し、structfunを使用してすべてのフィールドを反復処理し、興味のないフィールドをI & ...で無視します。

関連する問題