2015-03-17 2 views
3

У меня есть матрица АMatlab: выберите подматрицы из матрицы по определенным критериям

A=[f magic(10)] 
    A= 

931142103   92   99   1   8   15   67   74   51   58   40 
931142103   98   80   7   14   16   73   55   57   64   41 
931142103   4   81   88   20   22   54   56   63   70   47 
459200101   85   87   19   21   3   60   62   69   71   28 
459200101   86   93   25   2   9   61   68   75   52   34 
459200101   17   24   76   83   90   42   49   26   33   65 
459200101   23   5   82   89   91   48   30   32   39   66 
37833100   79   6   13   95   97   29   31   38   45   72 
37833100   10   12   94   96   78   35   37   44   46   53 
37833100   11   18   100   77   84   36   43   50   27   59 

Первый столбец тверды коды. Остальные столбцы - данные фирм, каждая строка относится к фирме в колонке 1 в конкретном году. Обратите внимание, что годы могут не быть балансом для каждой фирмы. Я хотел бы вычесть подматрицы в соответствии с первым столбцом. Например, для A(1:3,2:11) для 931142103:

A(1:3,2:11) 

ans = 

    92 99  1  8 15 67 74 51 58 40 
    98 80  7 14 16 73 55 57 64 41 
    4 81 88 20 22 54 56 63 70 47 

То же 459200101 (что было бы A(4:7,2:11)) и A(8:10,2:11) для 37833100.

Я получаю ощущение, что код должен нравится:

indices=find(A(:,1)); 
    obs=size(A(:,1)); 
    for i=1:obs, 
     if i==indices(i ??) 
      A{i}=A(??,2:11); 
     end 
    end 

Мне сложно индексировать эти сложные коды: 459200101 и 37833100, чтобы собрать их вместе. И как я могу написать строки моей подматрицы A{i}?

Большое спасибо!

ответ

3

Один подход с arrayfun -

%// Get unique entries from first column of A and keep the order 
%// with 'stable' option i.e. don't sort 
unqA1 = unique(A(:,1),'stable') 

%// Use arrayfun to select each such submatrix and store as a cell 
%// in a cell array, which is the final output 
outA = arrayfun(@(n) A(A(:,1)==unqA1(n),:),1:numel(unqA1),'Uni',0) 

Или это -

[~,~,row_idx] = unique(A(:,1),'stable') 
outA = arrayfun(@(n) A(row_idx==n,:),1:max(row_idx),'Uni',0) 

Наконец, вы можете проверить результаты с помощью вызова celldisp(outA)

+1

Вы быстро. :) – eigenchris

+0

Спасибо !!! Оно работает! Мой первый раз, чтобы узнать «массив», очень сильный. –

+0

@NicoleLeung Да, 'arrayfun' действительно удобен в таких ситуациях, когда нужны массивы ячеек! Подумайте о принятии решения, которое лучше всего подходит для вас? Подробнее о принятии решений [здесь] (http://meta.stackexchange.com/questions/5234/how-does-accepting-an-answer-work/5235#5235). – Divakar

3

Если значения в столбце 1 всегда появляются сгруппированные (как в вашем примере), вы можете использовать mat2cell следующим образом:

result = mat2cell(A, diff([0; find(diff(A(:,1))); size(A,1)])); 

Если они не делают, просто отсортировать строки A в соответствии с колонкой 1 перед нанесением выше:

A = sortrows(A,1); 
result = mat2cell(A, diff([0; find(diff(A(:,1))); size(A,1)])); 
2

Если вы не возражаете результаты внутренне не заказанные, вы можете использовать accumarray для этого:

[~,~,I] = unique(A(:,1),'stable'); 
partitions = accumarray(I, 1:size(A,1), [], @(I){A(I,2:end)});