質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
R

R言語は、「S言語」をオープンソースとして実装なおした、統計解析向けのプログラミング言語です。 計算がとても速くグラフィックも充実しているため、数値計算に向いています。 文法的には、統計解析部分はS言語を参考にしており、データ処理部分はSchemeの影響を受けています。 世界中の専門家が開発に関わり、日々新しい手法やアルゴリズムが追加されています。

Q&A

解決済

2回答

1863閲覧

Rで区分行列の積を計算したい。

jackojacko_

総合スコア17

R

R言語は、「S言語」をオープンソースとして実装なおした、統計解析向けのプログラミング言語です。 計算がとても速くグラフィックも充実しているため、数値計算に向いています。 文法的には、統計解析部分はS言語を参考にしており、データ処理部分はSchemeの影響を受けています。 世界中の専門家が開発に関わり、日々新しい手法やアルゴリズムが追加されています。

0グッド

0クリップ

投稿2017/12/16 11:14

Rで100列90万行の論理値からなる行列Aについて、クロス積(t(X) %*% X)を求めたいと思っています。
そのまま計算しようとしたところ、データが大きすぎてできなかったので、このページのように区分行列にブロック分けしてしたいと思っています。
しかしRでブロック行列を作るライブラリなどが見つからないので、どなたがご教授いただきたいです。
(Matrixライブラリでブロック対角行列は見つかったのですが、普通の区分行列を作る方法が知りたいです。)

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答2

0

R

1> a <- matrix(1:60, nrow=12) 2> a 3 [,1] [,2] [,3] [,4] [,5] 4 [1,] 1 13 25 37 49 5 [2,] 2 14 26 38 50 6 [3,] 3 15 27 39 51 7 [4,] 4 16 28 40 52 8 [5,] 5 17 29 41 53 9 [6,] 6 18 30 42 54 10 [7,] 7 19 31 43 55 11 [8,] 8 20 32 44 56 12 [9,] 9 21 33 45 57 13[10,] 10 22 34 46 58 14[11,] 11 23 35 47 59 15[12,] 12 24 36 48 60

これの逆行列のクロス積を求めることにします。

R

1> tcrossprod(a) 2 [,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8] [,9] [,10] [,11] [,12] 3 [1,] 4565 4690 4815 4940 5065 5190 5315 5440 5565 5690 5815 5940 4 [2,] 4690 4820 4950 5080 5210 5340 5470 5600 5730 5860 5990 6120 5 [3,] 4815 4950 5085 5220 5355 5490 5625 5760 5895 6030 6165 6300 6 [4,] 4940 5080 5220 5360 5500 5640 5780 5920 6060 6200 6340 6480 7 [5,] 5065 5210 5355 5500 5645 5790 5935 6080 6225 6370 6515 6660 8 [6,] 5190 5340 5490 5640 5790 5940 6090 6240 6390 6540 6690 6840 9 [7,] 5315 5470 5625 5780 5935 6090 6245 6400 6555 6710 6865 7020 10 [8,] 5440 5600 5760 5920 6080 6240 6400 6560 6720 6880 7040 7200 11 [9,] 5565 5730 5895 6060 6225 6390 6555 6720 6885 7050 7215 7380 12[10,] 5690 5860 6030 6200 6370 6540 6710 6880 7050 7220 7390 7560 13[11,] 5815 5990 6165 6340 6515 6690 6865 7040 7215 7390 7565 7740 14[12,] 5940 6120 6300 6480 6660 6840 7020 7200 7380 7560 7740 7920

行列を縦にk分割します。

R

1> k <- 4 #分割する数 2#分割 3> blocks <- lapply(1:k, 4 function(x) { 5 nrow_b <- nrow(a)/k 6 start <- nrow_b*(x-1)+1 7 end <- nrow_b*x 8 return(a[start:end,]) 9 } 10 ) 11> blocks 12[[1]] 13 [,1] [,2] [,3] [,4] [,5] 14[1,] 1 13 25 37 49 15[2,] 2 14 26 38 50 16[3,] 3 15 27 39 51 17 18[[2]] 19 [,1] [,2] [,3] [,4] [,5] 20[1,] 4 16 28 40 52 21[2,] 5 17 29 41 53 22[3,] 6 18 30 42 54 23 24[[3]] 25 [,1] [,2] [,3] [,4] [,5] 26[1,] 7 19 31 43 55 27[2,] 8 20 32 44 56 28[3,] 9 21 33 45 57 29 30[[4]] 31 [,1] [,2] [,3] [,4] [,5] 32[1,] 10 22 34 46 58 33[2,] 11 23 35 47 59 34[3,] 12 24 36 48 60

この区分行列ごとに行列積を計算します。

R

1> result_blocks <- lapply(1:k, 2 function(row) {return(lapply( 3 1:k, 4 function(col) { 5 return( 6 tcrossprod(blocks[[row]],blocks[[col]]) 7 ) 8 } 9))})

二重リストの中に行列が入っている状態ができるので、データフレームに戻します。

R

1> result<- rbindlist(lapply( 2 1:k, 3 function(row_b) { 4 return(data.frame(result_blocks[[row_b]][1:k]))} 5 )) 6> result 7 X1 X2 X3 X1.1 X2.1 X3.1 X1.2 X2.2 X3.2 X1.3 X2.3 X3.3 8 1: 4565 4690 4815 4940 5065 5190 5315 5440 5565 5690 5815 5940 9 2: 4690 4820 4950 5080 5210 5340 5470 5600 5730 5860 5990 6120 10 3: 4815 4950 5085 5220 5355 5490 5625 5760 5895 6030 6165 6300 11 4: 4940 5080 5220 5360 5500 5640 5780 5920 6060 6200 6340 6480 12 5: 5065 5210 5355 5500 5645 5790 5935 6080 6225 6370 6515 6660 13 6: 5190 5340 5490 5640 5790 5940 6090 6240 6390 6540 6690 6840 14 7: 5315 5470 5625 5780 5935 6090 6245 6400 6555 6710 6865 7020 15 8: 5440 5600 5760 5920 6080 6240 6400 6560 6720 6880 7040 7200 16 9: 5565 5730 5895 6060 6225 6390 6555 6720 6885 7050 7215 7380 1710: 5690 5860 6030 6200 6370 6540 6710 6880 7050 7220 7390 7560 1811: 5815 5990 6165 6340 6515 6690 6865 7040 7215 7390 7565 7740 1912: 5940 6120 6300 6480 6660 6840 7020 7200 7380 7560 7740 7920

正しい計算ができました!

投稿2017/12/16 14:24

jackojacko_

総合スコア17

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

ベストアンサー

やりたいのはこういうことでしょうか?

R

1a <- matrix(1:60, nrow=6) 2rwidth <- 3 3cwidth <- 5 4for(rr in seq(1, nrow(a)/rwidth)*rwidth-rwidth+1){ 5 for(cc in seq(1, ncol(a)/cwidth)*cwidth-cwidth+1){ 6 print(paste("matrix for",rr,cc)) 7 pmatrix <- a[c(rr:(rr+rwidth-1)), c(cc:(cc+cwidth-1))] 8 print(pmatrix) 9 } 10}

投稿2017/12/16 11:55

KojiDoi

総合スコア13669

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

jackojacko_

2017/12/16 14:15

for文回せばいいのですね!ありがとうございます 行列積の計算がしたかったので、これをヒントに作ることができました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問