2

sの2092x252行列があり、を使用するループdoubleを作成する必要があります。この例についてだけ言いましょう。ループを実行するために必要なのは、各列をインデックスとして使用して実行することです。たとえば、列1をインデックスとして指定すると、列2:252との差が(を使用して)取得されます。次に、列2をインデックスとして設定し、列3:252との差を取得します(ここでも)を使用します。ループは。まで実行し続ける必要があります。forbsxfunbsxfun(@minus)bsxfun(@minus)bsxfun(@minus)bsxfun(@minus)bsxfun(@minus, 251, 252)

出力は、251個の変数ではなく1つの変数になります。合計31626のデータポイントがあります。

また、コードについて教えてください。

4

2 に答える 2

3

これがまさにあなたが望んでいたものかどうかはわかりません.31626x2092のデータポイントになりますが、列の差を取ると言ったので...

data=ceil(rand(7,5)*10); % some sample data, works with any matrix(at least 2 columns of course)

N = size(data,2);

%b=cell(N-1,1);
c=NaN(size(data,1),N*(N-1)/2); % preallocate result matrix

kk=0;
for ii=1:N-1
    %b{ii} = bsxfun(@minus,data(:,ii),data(:,ii+1:end));
    c(:,kk+(1:N-ii)) = bsxfun(@minus,data(:,ii),data(:,ii+1:end));
    kk=kk+N-ii;
end

ここで重要なのは、各ループステップで、操作を実行したいマトリックスの部分のみを選択することですminus。つまり、data(:,ii)(= ii 番目の列) およびdata(:,ii+1:end)(= ii 番目からマトリックスの終わり)

bsxfun 関数の説明には次のように書かれて
います。

そのシングルトン展開は、ここで使用しているものです。bsxfun は、2 つの入力が 1 つの列であり、同じサイズの列を持つ行列であることを認識し、列を行列と同じサイズになるように展開します (= シングルトン展開 (行の次元が展開されます) )

したがって、行を互いに減算したい場合は、行と前と同じ行列を提供するだけで、行ベクトルを列の次元に沿って拡張することもできます。

N = size(data,1);

%b=cell(N-1,1);
c=NaN(N*(N-1)/2,size(data,2)); % preallocate result matrix

kk=0;
for ii=1:N-1
    %b{ii} = bsxfun(@minus,data(ii,:),data(ii+1:end,:));
    c(kk+(1:N-ii),:) = bsxfun(@minus,data(ii,:),data(ii+1:end,:));
    kk=kk+N-ii;
end

ご覧のとおり、すべての行列のインデックス付けの場所が入れ替わり、 にA(i,j)変更されましたA(j,i)

ループの各ステップで結果マトリックスにセルを使用すると、結果に簡単にアクセスできますが、結果を 1 つの変数 (私が推測するマトリックス) で取得する必要があるため、それらをコメントアウトしました。

編集

事前割り当てについて: http://www.mathworks.nl/help/techdoc/matlab_prog/f8-784135.html

c(:,kk+(1:N-ii));
kk=kk+N-ii

最もトリッキーなインデックス付けです:
ii=1 の場合、挿入する列が 251 あります: 出力変数の列 1->251
ii=2 -> 250 列、出力の列 252->501 になります。
ii=3 -> 249 列、出力の列 502->750
ii=4 => 248 列、出力の列 751->999
など

kk+(1:N-ii)出力に適切な列を選択しますbsxfun
変数kkは、すでに出力変数に保存されている列の数であるcため、明らかにゼロから始まります。これを別の値、たとえば に変更するとkk_init、 の最初のkk_init列はc空のままになり、結果のc行列にはN*(N-1)/2+kk_initの代わりに列が含まれますN*(N-1)/2

于 2012-05-31T10:56:41.213 に答える
1

インデックスを追跡する必要がないように、結果を計算して cell 配列に格納し、すべてのセルを 1 つの行列に連結できます。

data = rand(2092,252);
C = arrayfun(@(k) bsxfun(@minus, data(:,k), data(:,k+1:end)), ...
        1:size(data,2)-1, 'UniformOutput',false);
C = horzcat(C{:});

結果のマトリックス:

>> whos C
  Name         Size                   Bytes  Class     Attributes

  C         2092x31626            529292736  double   
于 2012-06-01T01:16:59.727 に答える