有没有一种快速的方法来计算矩阵中项目的出现次数并将它们保存在另一个矩阵中而不使用循环?

Kri*_*673 0 matlab matrix

我有一个时间序列矩阵X,其第一列包含用户ID,第二列包含他们在不同时间使用的项目ID:

X=[1 4
  2 1
  4 2
  2 3
  3 4
  1 1
  4 2
  5 3
  2 1
  4 2
  5 4];
Run Code Online (Sandbox Code Playgroud)

我想找出哪个用户使用了多少次项,并将其保存在矩阵Y中.Y的行以ID的升序表示用户,列按ID的升序表示项:

Y=[1    0   0   1
   2    0   1   0
   0    0   0   1
   0    3   0   0
   0    0   1   1]
Run Code Online (Sandbox Code Playgroud)

我用来查找矩阵Y的代码使用2个for循环,这对我的大数据来说是笨重的:

no_of_users = size(unique(X(:,1)),1);
no_of_items = size(unique(X(:,2)),1);
users=unique(X(:,1));
Y=zeros(no_of_users,no_of_items);

for a=1:size(A,1)
    for b=1:no_of_users
        if X(a,1)==users(b,1)
            Y(b,X(a,2)) = Y(b,X(a,2)) + 1;
        end
    end
end
Run Code Online (Sandbox Code Playgroud)

有更多时间有效的方法吗?

bea*_*ker 7

sparse从行/列索引创建稀疏矩阵,如果给出标量值1,则可以方便地累计出现次数.只需转换为完整矩阵即可.

Y = full(sparse(X(:,1), X(:,2), 1))

Y =

   1   0   0   1
   2   0   1   0
   0   0   0   1
   0   3   0   0
   0   0   1   1
Run Code Online (Sandbox Code Playgroud)

但是如评论中所建议的那样,使用accumarray可能更快:

>> Y2 = accumarray(X, 1)

Y2 =

   1   0   0   1
   2   0   1   0
   0   0   0   1
   0   3   0   0
   0   0   1   1
Run Code Online (Sandbox Code Playgroud)

(在Octave,sparse似乎需要大约50%的时间accumarray.)