3

私は、独自の形式から一連の構造にデータをロードする Matlab API を使用しています。ファイルをロードした後のデータセットの例を次に示します。

>>fieldnames(データ(1))

ans =

'Grid_Point_ID'
'Grid_Point_Latitude'
'Grid_Point_Longitude'
'Grid_Point_Altitude'
'Grid_Point_Mask'
'BT_Data'

>> data(1).BT_Data

ans =

BT_Data: [1x66 struct]

>> fieldnames(data(1).BT_Data(1))

ans =

'Flags'
'BT_Value_Real'
'BT_Value_Imag'
'Pixel_Radiometric_Accuracy'
'Incidence_Angle'
'Azimuth_Angle'
'Faraday_Rotation_Angle'
'Geometric_Rotation_Angle'
'Snapshot_ID_of_Pixel'
'Footprint_Axis1'
'Footprint_Axis2'

すべてをループしたいdata(i).BT_Data(j)。私はすでにdata罰金の長さを取得していますが、サイズ/長さを取得できませんBT_Data(これは ごとに異なりますdata(i)):

>> 長さ(データ(1).BT_Data)

ans =

 1

>> size(data(1).BT_Data)

ans =

 1     1

ここで期待される結果はans = 66(または の同等の配列size()) です。

私は構造データ形式にあまり詳しくありませんが、それが私の苦労の一部かもしれません。しかし、length(data)うまく機能したので、なぜ機能しないのか混乱していますBT_Data(私も試しましたBT_Data(:))。

私が見つけることができる最も関連性の高い以前の回答は1757250ですが、機能させることができませんでした (ここでは当てはまらないと思います)。あなたが提供できる洞察に感謝します。

------編集------

ここでは、API を使用して現在のポイントに到達する方法について、もう少し洞察を示します。

>> system('ln -sf /opt/rwapi-matlab/lib/rwapi/smos/config/xml_rw_api.usr_conf.xml .');
setenv('XML_RW_API_HOME','/opt/rwapi-matlab/lib/rwapi');
パス (パス、'/opt/rwapi-matlab');

>> 製品 = RWAPI.product('SM_OPEB_MIR_SCLF1C_20110202T013659_20110202T014642_346_060_1')

Array SMOS Matlab Interface バージョン 1.4
(c) 2010 Array Systems Computing Inc. of Canada ( http://www.array.ca )
このソフトウェアの配布または変更には、Array からの書面による許可が必要です

製品 =

RWAPI.product handle
Package: RWAPI

Properties:
     filename: 'SM_OPEB_MIR_SCLF1C_20110202T013659_20110202T014642_346_060_1'
       header: [1x1 struct]
xml_datablock: []

メソッド、イベント、スーパークラス

>> データ = prod.dataset(2)

データ =

プロパティのない RWAPI.dataset ハンドル。パッケージ: RAPI

メソッド、イベント、スーパークラス

>> データ(1)

ans =

       Grid_Point_ID: 251721
 Grid_Point_Latitude: 25.5000
Grid_Point_Longitude: -102.2590
 Grid_Point_Altitude: 1.4714e+03
     Grid_Point_Mask: 2
             BT_Data: [1x66 struct]

>> data(1).BT_Data

ans =

BT_Data: [1x66 struct]

>> データ(1).BT_Data(1)

ans =

                     Flags: 6229
             BT_Value_Real: 262.5275
             BT_Value_Imag: 0
Pixel_Radiometric_Accuracy: 6160
           Incidence_Angle: 31966
             Azimuth_Angle: 10299
    Faraday_Rotation_Angle: 65277
  Geometric_Rotation_Angle: 58605
      Snapshot_ID_of_Pixel: 65752530
           Footprint_Axis1: 19649
           Footprint_Axis2: 14625

>> whos
名前 サイズ バイト クラス 属性

ans 1x1 1 論理
データ 1x19091 112 RWAPI.dataset
prod 1x2 112 RWAPI.product

4

3 に答える 3

2

わかりました、これらの RWAPI クラスでオーバーライドされた subsref メソッドの異常だと思います。少し病的な subsref でクラスを定義することにより、観察されたすべての動作を再現することができました。

classdef stupidref
    %STUPIDREF Reproduce odd indexing behavior that jpatton saw. Buggy.
    properties
        BT_Data = repmat(struct('foo',42, 'bar',42), [1 66]);
    end
    methods
        function B = subsref(A,S)
            s = S(1);
            subs = s.subs;
            chain = S(2:end);

            switch s.type
                case '()'
                    B = builtin( 'subsref', A, s );
                    if ~isempty(chain)
                        B = subsref(B, chain);
                    end

                case '.'
                    % Non-standard behavior!
                    if ~isempty(chain) && isequal(chain(1).type, '()')
                        B = subsref(A.(s.subs), chain);
                    else
                        B = struct(s.subs, A.(s.subs));
                    end
            end
        end
    end
end

これは、 と の奇妙な違い、data(1).BT_Dataおよびfieldnames(data(1).BT_Data(1))".BT_Data" を繰り返し追加するタブ補完と一致しています。

>> data = stupidref;
>> data(1).BT_Data
ans = 
    BT_Data: [1x66 struct]
>> fieldnames(data(1).BT_Data)
ans = 
    'BT_Data'
>> fieldnames(data(1).BT_Data(1))
ans = 
    'foo'
    'bar'
>> length(data(1).BT_Data)
ans =
     1
>> data(1).BT_Data.BT_Data.BT_Data.BT_Data.BT_Data.BT_Data % produced by tab-completion
ans = 
    BT_Data: [1x66 struct]
>> 

あなたの回避策は良いです-一度呼び出すとa = data(1).BT_Data、通常の構造体が得られ、非標準のsubsrefは邪魔になりません。を使用してワンライナーで同じ効果を得ることができますgetfield

>> btdata = getfield(data(1).BT_Data, 'BT_Data')
btdata = 
1x66 struct array with fields:
    foo
    bar

これはバグの可能性があるので、RWAPI ライブラリの作成者に報告します。

このコードを独自の回避策の回答に自由に編集してください。診断をサポートするほど、実際には答えではありません。

于 2011-02-04T20:40:54.017 に答える
2

回避策を見つけましたが、それほど満足できるものではありません:

>> a = data(1).BT_Data

a =

BT_Data: [1x66 struct]

>> 長さ(a.BT_Data)

ans =

66

他に「適切な」方法があるとは思えないので、今のところこれを答えとしてマークします。

アンドリューの答えは、問題を本当に突き止めました(そして、この回避策が機能する理由)。

于 2011-02-04T19:30:53.540 に答える
1

結果のいくつかは矛盾しているようです。手始めに、フィールドBT_Dataに1 x 66の構造体配列が含まれている場合、次のような出力が表示されると思います。

>> data(1).BT_Data

ans =

1x66 struct array with fields:
     Flags
     ...    %# etc.

あなたがこれを見るという事実:

>> data(1).BT_Data

ans =

BT_Data: [1x66 struct]

BT_Dataこれは、実際にはBT_Data、と呼ばれる1つのフィールドを持つ1行1列の構造体であり、そのフィールドには1行66列の構造体配列が含まれていることを示唆しています。BT_Dataこれは、最初の(1行1列の構造)の長さとサイズを取得したときに表示される内容を説明します。この場合、次の結果が得られるはずです。

>> size(data(1).BT_Data.BT_Data)

ans =

     1     66

ただし、これでも、次の場合に表示される出力については説明されていません。

fieldnames(data(1).BT_Data(1))

それは私を失望させています。これを行うことBT_Dataで、実際には構造であり、インデックス作成と表示の動作が異なる可能性のある他のタイプのオブジェクトではないことを確認できます。

isstruct(data(1).BT_Data)

1そして、これはifBT_Dataが構造体であることを返すはずです。

于 2011-02-03T22:47:57.483 に答える