#r #matlab
#r #matlab
Вопрос:
Я думаю, у меня есть двухуровневый вопрос, относящийся к diag
R и matlab.
1) Мне было интересно, существует ли уже разработанный способ доступа к различным диагоналям матриц в R аналогично тому, как это делается в Matlab (см. http://www.mathworks.com/help/techdoc/ref/diag.html ).
2) Если текущей функции еще нет, как можно улучшить мой код, чтобы он был похож на R diag
, где
diag(x = 1, nrow, ncol) # returns the values of the diagonal
diag(x) <- value # inserts values on the diagonal
В настоящее время мой код возвращает элементы по диагонали с заданным значением k, но как его можно записать так, чтобы, если он указан как второй способ (выше), он позволял мне вставлять значения по диагонали. В настоящее время для этого я использую diag.ind
, чтобы указать индексы, а затем использовать эти индексы для вставки значений по диагонали k.
Вот код:
'diag.ind'<-function(x,k=0){
if(k=='') k=0
x<-as.matrix(x)
if(dim(x)[2]==dim(x)[1]){
stp_pt_r<-dim(x)[1]
stp_pt_c<-dim(x)[2]
}
if(ncol(x)> dim(x)[1]){
stp_pt_r<-dim(x)[1]
stp_pt_c<-stp_pt_r 1
}
if(ncol(x)< dim(x)[1]){
stp_pt_c<-dim(x)[2]
stp_pt_r<-stp_pt_c 1
}
if(k==0){
r<-as.matrix(seq(1,stp_pt_r,by=1))
c<-as.matrix(seq(1,stp_pt_c,by=1))
ind.r<- cbind(r,c)
}
if(k>0){
r<-t(as.matrix(seq(1,stp_pt_r,by=1)))
c<-t(as.matrix(seq((1 k),stp_pt_c,by=1)))
ind<-t(rbind.fill.matrix(r,c))
ind.r<-ind[!is.na(ind[,2]),]
}
if(k<0){
k<-abs(k)
r<-t(as.matrix(seq((1 k),stp_pt_r,by=1)))
c<-t(as.matrix(seq(1,stp_pt_c,by=1)))
ind<-t(rbind.fill.matrix(r,c))
ind.r<-ind[!is.na(ind[,1]),]
}
diag.x<-x[ind.r]
output<-list(diag.x=diag.x, diag.ind=ind.r)
return(output)
}
Это довольно неуклюже, и я чувствую, что должен изобретать велосипед. Заранее спасибо за любую информацию!
Ответ №1:
После вашего ответа на Andrie это может удовлетворить:
exdiag <- function(mat, off) {mat[row(mat) off == col(mat)]}
x <- matrix(1:16, ncol=4)
exdiag(x,1)
#[1] 5 10 15
Я думал, вам нужна функция, которая может назначать или возвращать одну из диагональных или суб- или супердиагональных матриц, это функция конструктора:
subdiag <- function(vec, size, offset=0){
M <- matrix(0, size, size)
M[row(M)-offset == col(M)] <- vec
return(M)}
> subdiag(1, 5, 1)
[,1] [,2] [,3] [,4] [,5]
[1,] 0 0 0 0 0
[2,] 1 0 0 0 0
[3,] 0 1 0 0 0
[4,] 0 0 1 0 0
[5,] 0 0 0 1 0
Вызываемый только с двумя аргументами, вы получите диагональную матрицу. Вы можете создавать супердиагональные матрицы с отрицательными смещениями. Если это то, что вы хотели для конструктора, то не должно быть слишком сложно создать аналогичную subdiag<-
функцию, чтобы она соответствовала ей.
Комментарии:
1. Отлично, это то, что я искал, и намного проще, чем мой код. Спасибо!
Ответ №2:
В MATLAB, чтобы присвоить значения x
диагонали A
:
n = size(A,1);
A(1:n 1:end) = x
Найдите линейную индексацию.
Хотя, возможно, это не то, что вы просили.