21

repR for Matlabの関数と同様に動作する関数を探しています。たとえばrep、次のことができます。

> rep(c(1,2,3),times=3)
[1] 1 2 3 1 2 3 1 2 3

> rep(c(1,2,3),each=3)
[1] 1 1 1 2 2 2 3 3 3
> 

matlab には、最初の部分を達成する repmat 関数があります

>> repmat([1,2,3],1,3)

ans =

     1     2     3     1     2     3     1     2     3

2番目の部分ではありません(または、少なくとも方法がわかりません)。

助言がありますか?

4

4 に答える 4

8

良い質問 +1。これを達成するためのきちんとしたワンライナーの方法は、クロネッカー テンソル積を使用することです。

A = [1 2 3];
N = 3;
B = kron(A, ones(1, N));

それで:

B =

     1     1     1     2     2     2     3     3     3

更新: @Dan は、私のkron方法よりも効率的であると思われる非常に優れたソリューションを提供しました。そのため、ページを離れる前にその回答を確認してください :-)

更新: @bcumming は、入力ベクトルが大きい場合に非常にうまくスケーリングする優れたソリューションも提供しています。

于 2013-01-30T23:03:37.310 に答える
6

私のように、クロネッカー テンソル積が何であるかわからない場合は、このより直感的な (そして実際には私がより速く考える) ソリューションに興味があるかもしれません。

c(ceil((1:length(c)*n)/n));

そのため、ここではベクトル インデックスを使用して行列を複製しました。たとえば、上記の 2 つのケースを使用すると、次のことができます。

c = 1:3;
c([1 1 1 2 2 2 3 3 3]) %for each
c([1 2 3 1 2 3 1 2 3]) %for times

したがって、問題は、あなたが要求している機能そのものを持たないベクトル [1 2 3 1 2 3 1 2 3] をどのように作成するかです。そこで、必要な要素数、つまり 1:9 のベクトルを作成し、3 で割って切り上げます (つまりceil((1:9)/3)、コマンド ラインで試してください。

ちょっとしたベンチマーク (私はこれがループにある必要があることを知っているので、これはあまり正確ではないかもしれません):

c = 1:3; n = 3;
tic; k = kron(c, ones(1, n)); toc; % 0.000208 seconds.
tic; a = c(ceil((1:length(c)*n)/n)); toc;  % 0.000025 seconds.
clear;
c = 1:1000000; n = 3;
tic; k = kron(c, ones(1, n)); toc; % 0.143747 seconds.
tic; a = c(ceil((1:length(c)*n)/n)); toc;  % 0.090956 seconds.
clear;
c = 1:10000; n = 1000;
tic; k = kron(c, ones(1, n)); toc; % 0.583336 seconds.
tic; a = c(ceil((1:length(c)*n)/n)); toc;  % 0.237878 seconds.
于 2013-01-31T06:50:50.680 に答える
1

ここに1つのアイデアがあります:

a=[1,2,3];
reshape(repmat(a,1,length(a)),1,length(a)^2)

ans =

 1     2     3     1     2     3     1     2     3

reshape(repmat(a,length(a),1),1,length(a)^2)

ans =

 1     1     1     2     2     2     3     3     3

これを 1 つのステップで行う単純な関数をまだ見つけることができませんが、もしあれば興味があります。

于 2013-01-30T22:53:00.787 に答える