2

I have a matrix A = [1 2 4 4 8 8 8 4 1 7 7 8 8 9] and I want to create a new matrix which has number of same elements in A.

I have two 1, one 2, three 4, two 7, five 8 and one 9.

My new matrix should be [numbers;amount of each number]

newmatrix = [1 2 4 7 8 9; 2 1 3 2 5 1]

How can I create new matrix from A?

Stewie Griffin
  • 14,889
  • 11
  • 39
  • 70
ffttyy
  • 853
  • 2
  • 19
  • 49

2 Answers2

4
  1. Standard, recommended approach: use unique and histc:

    uA = unique(A);
    result = [uA; histc(A, uA)];
    
  2. Another possibility is to do the counting with sparse, and then use nonzeros to extract the values and find to get the indices:

    s = sparse(1,A,1);
    result = [find(s); nonzeros(s).'];
    

    This second approach seems to be faster for small A, but the first is the recommended approach in general.

Luis Mendo
  • 110,752
  • 13
  • 76
  • 147
  • ... but about twice as slow for larger `A`'s if my benchmarking results are correct. Anyway, I like the approach =) – Stewie Griffin Aug 18 '14 at 12:21
  • @RobertP. Yes, it's more of a curiosity than anything. I've edited the answer to state that the standard and recommended approach is the first – Luis Mendo Aug 18 '14 at 12:22
1

You can do this by combining unique and histc like this:

newmatrix = [unique(A); histc(A, unique(A))]

The unique function returns a list of all the numbers in your vector, whereas histc counts each occurrence of the unique value in the original vector.

Note that for large vectors, Luis' answer will be faster as it only calls unique once. However, if you're one of those who prefer one-liners, this answer should do the trick.

If your vector might be either vertical or horizontal, you the above will result in a 2nx1 vector instead of a nx2 matrix. One possibility would be to call reshape like this:

result = reshape([uA; histc(A, uA)],[],2);
Community
  • 1
  • 1
Stewie Griffin
  • 14,889
  • 11
  • 39
  • 70