2015-04-23 14 views
6

Mam wektor takiego w R:Wstaw numer powyżej przekątnej macierzy R

vec1 <- c(14000,12000,8000) 

Próbuję utworzyć macierz gdzie 14000 to mój główny przekątna, 1200 to jeden powyżej przekątnej, 8000 dwa powyżej przekątnej.

Jestem zaznajomiony z robieniem tego w Pythonie/numpy, ale nie mogę go rozgryźć w R (lub przynajmniej skuteczny sposób to zrobić). Idealnie wyjście będzie wyglądać następująco:

14000 12000 8000 
    0 14000 12000 
    0  0 14000 
+0

(tępy) jedna wkładka 't (sapply (1: 3 , function (x) c (rep (0, x - 1), head (vec1, 4 - x)))) ' – rawr

Odpowiedz

6

Spróbuj

m1 <- t(matrix(vec1, nrow=5, ncol=3))[,1:3] 
m1[lower.tri(m1)] <- 0 
m1 
#  [,1] [,2] [,3] 
#[1,] 14000 12000 8000 
#[2,]  0 14000 12000 
#[3,]  0  0 14000 

, lub toeplitz

toeplitz(vec1)*upper.tri(diag(seq_along(vec1)), diag=TRUE) 
#  [,1] [,2] [,3] 
#[1,] 14000 12000 8000 
#[2,]  0 14000 12000 
#[3,]  0  0 14000 

lub zmodyfikowanym sugerowane przez @David Arenburg

m <- toeplitz(vec1) 
m[lower.tri(m)] <- 0 
+0

@DavidArenburg Myślałem o przejściu trasy 'lower.tri (m)', ale zdecydowałem się na to w jednej linii. – akrun

+0

@DavidArenburg Dzięki za komentarze. Dodałem opcję sugerowaną przez ciebie .. – akrun

+0

Twoja odpowiedź jest lepsza niż moja; dobrze się skaluje. Szczególnie lubię 'toeplitz()'. +1 –

1

W tym prostym przypadku można przypisać ukośne i górne trójkątne porcje oddzielnie tak:

m <- matrix(0, nrow=3, ncol=3) 

diag(m) <- 14000 

m[upper.tri(m)] <- c(12000, 8000, 12000) 

Jednakże, jak David Arenburg podkreślić, że jest to bardziej podejście ręczne, a tym samym nie skaluje się dobrze. Aby uzyskać bardziej zautomatyzowane i skalowalne podejście, polecam rozwiązanie firmy Akrun, używając toeplitz() i lower.tri().

Będę tu trzymał tę odpowiedź ze względu na jej kompletność, ale uważam, że akrun jest lepszym ogólnym rozwiązaniem.

+0

' diag (m) <- 14000' i 'm [upper.tri (m)] < - c (12000, 8000, 12000) dla mnie bardzo ręczna. Jak byś to zrobił z przypadkowym wektorem? –

Powiązane problemy