Digamos que tengo 5 matrices de diferentes tamaños. Todas las matrices tienen el mismo número de columnas, en mi caso 2, pero un número diferente de filas. Necesito encontrar los elementos de las filas que aparecen en al menos 3 de tales matrices.

En este momento, comparo dos matrices usando ismember, luego comparo ese resultado con la tercera matriz y luego guardo los valores de fila que ocurren en las tres matrices. Hago esto para cada combinación posible de 3 matrices; básicamente en mi caso, tengo 10 de tales operaciones en total. Es como elegir tres de 5 sin repeticiones.

Funciona, pero estoy buscando una implementación más eficiente. En particular, estaba buscando cualquier implementación que pueda realizar esto votando. Es como tener conjuntos de diferentes tamaños y tratar de encontrar los elementos que aparecen en la mayoría de conjuntos, en mi caso 3 matrices de 5.

0
Miranda 15 nov. 2017 a las 22:07

2 respuestas

La mejor respuesta

No estoy seguro de lo que quiere decir con votar, pero creo que hace lo que busca.

Crea 1 gran matriz única de todas las filas de las matrices. Hace un ismember por filas de la matriz única con cada matriz individual. El ismember se suma para obtener un recuento de cuántas veces existe cada fila única en su conjunto de matrices.

Luego puede usar ese recuento para devolver una nueva matriz que tenga al menos minNum apariciones.

Lo llamarías así:

>> [outRows, uRows, memCount]= getRowDuplicates(3,a,b,c,d,e)

Donde a, b, c, d, e son sus matrices y 3 es el número mínimo de ocurrencias

function [outRows, uRows, memCount]= getRowDuplicates(minNum,varargin)

uRows = unique(vertcat(varargin{:}),'rows');
memCount = false(size(uRows,1),1);
for j = 1:nargin-1
    memCount = memCount + ismember(uRows,varargin{j},'rows');    
end
rowIdx = memCount >= minNum;
outRows = uRows(rowIdx,:);
1
Aero Engy 15 nov. 2017 a las 20:58

¡Gracias a Aero Engy por la solución! Este es mi propio intento, después de reescribir mi implementación inicial, no muy eficiente. Pensé que alguien podría encontrarlo útil:

function [majorityPts] = MajorityPointSelection(Mat, numMajority)
    result = vertcat(Mat{:});
    allUniq = unique(result(:,1:2),'rows');
    numUniq = size(allUniq,1);

    allUniq = [allUniq zeros(numUniq,1); zeros(size(result,1)-numUniq, 3)];
    for i = 1:numUniq
        sumNumRow = sum(result(:,1:2) == allUniq(i,1:2),1);
        allUniq(i,3) = sumNumRow(1);
    end

    allUniq(numUniq+1:end,:) = [];
    majorityPts = allUniq(allUniq(:,3)>=numMajority,1:2);
end

Aquí Mat es una celda que contiene todas las matrices que quiero comparar para encontrar las filas que aparecen en al menos numMajority de ellas, donde en mi caso numMajority = 3. Básicamente, primero vuelco todas las matrices en una matriz grande (result) y luego encuentro las filas únicas de esta matriz. Finalmente, cuento el número de cada fila única y devuelvo los puntos que aparecen en la mayoría de matrices como majorityPts.

0
Miranda 18 nov. 2017 a las 21:11