Find complementary column combination of a matrix
    2 visualizzazioni (ultimi 30 giorni)
  
       Mostra commenti meno recenti
    
Hello! Need your help!
I have a 30x9 matrix A filled with 0, 4, 8.
Get the matrix MaxA where A has its maxima per row:
V = max(A,[ ],2);
MaxA = A==V;
And now i want the indices of the minimum combination of colmuns that gets me a complete column filled with 1, so after all the most complementary columns. 
Example:
A = [8 4 0 8 8                   [1 0 0 1 1
     4 8 0 8 0            MaxA =  0 1 0 1 0         
     4 0 4 0 0]                   1 0 1 0 0]
-> column 1 and 2 of MaxA give me
Result = [1 2  (column 1 and 2)                                  
          1 4  (column 1 and 4)      -> give me a column with [1; 1; 1]
          3 4] (column 3 and 4) 
-> column 2, 3 and 5 does the same but i would net 3 instead of 2 columns
Many thanks in advance!!!
0 Commenti
Risposta accettata
  Bruno Luong
      
      
 il 16 Apr 2022
        
      Modificato: Bruno Luong
      
      
 il 19 Apr 2022
  
      I start with MaxA, brute force method
% Dummy test
A = [8 4 0 8 8  
     4 8 0 8 0   
     4 0 4 0 0];
V = max(A,[ ],2);
MaxA = A==V;
% Algo starts here
n = size(MaxA,2);
% each row c(i,:) of c stores a subset of colums of A
% c(i,j) is 1 if the ci=olumns c is in the subset
% there are 2^n subset.
c = dec2bin(0:2^n-1)-'0';
% number of columns (cardinal of the subset of column);
sc = sum(c,2);
% Find which subsets have "complementary" by adding all the subset columns
% of maxA, using matrix multiplication trick and observe if the
% product have all elements > 0
j = find(all(MaxA*c',1));
% Find candidate subset
if ~isempty(j)
    % find the minimum of cardinals (umber of columns)
    nc = min(sc(j));
    % select all solution having the same cardinal (==nc)
    % find returns the list of nc x nr columns, nr is the number of subsets
    [col,~] = find(c(j(sc(j)==nc),:)');
    % reshape and transpose to put in the shape you want
    Result = reshape(col,nc,[])';
else
    Result = [];
end
Result
9 Commenti
  Bruno Luong
      
      
 il 19 Apr 2022
				This is the implementation with preprocess of finding candidate by Matt's minL1intlin
% Dummy test
A = [8 4 0 8 8  
     4 8 0 8 0   
     4 0 4 0 0]
V = max(A,[ ],2);
MaxA = double(A==V);
[m,n] = size(MaxA);
% Find a candidate of complementary using Matt's FEX
% https://www.mathworks.com/matlabcentral/fileexchange/52795-constrained-minimum-l1-norm-solutions-of-linear-equations 
% This relies on the good convergence of minL1intlin
em = ones(m,1);
en = ones(n,1);
Candidate = minL1intlin(speye(n),0*en,1:n,-MaxA,-em,[],[], 0*en, 1*en);
if ~isempty(Candidate)
    % solution exists
    nc = sum(Candidate);
    % all combinations of nc-columns among n 
    j = nchoosek(1:n, nc);
    p = size(j,1); % nchoosek(n, nc)
    % each row c(i,:) of c stores a subset of colums of A
    % c(i,j) is 1 if the columns c is in the subset
    % there are p subsets with nc columns.
    i = repmat((1:p)', 1, nc);
    c = sparse(i, j, 1, p, n);
    % Only keep those who meet
    Result = j(all(MaxA*c',1),:);
else
    Result = [];
end
Result  
Più risposte (1)
  Matt J
      
      
 il 16 Apr 2022
        
      Modificato: Matt J
      
      
 il 16 Apr 2022
  
      Do you need all combinations or just one of the minimium-length combinations? If the latter, then download minL1intlin
and,
 MaxA = [1 0 0 1 1
        0 1 0 1 0         
        1 0 1 0 0];
 [m,n]=size(MaxA);
  em=ones(m,1);
  en=ones(n,1);
Result = find( minL1intlin(speye(n),0*en,1:n,[],[],MaxA,em,0*en,1*en) )'
4 Commenti
  Bruno Luong
      
      
 il 19 Apr 2022
				
      Modificato: Bruno Luong
      
      
 il 19 Apr 2022
  
			What nc value returned when there is no admissible solution?
Vedere anche
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!