Превращение диагоналей матрицы в столбцы
Я ищу матричную операцию формы: B = M*A*N
где A
некоторая общая квадратная матрица и M
а также N
это матрицы, которые я хочу найти. Такие, что колонны B
являются диагоналями A
, В первом столбце главная диагональ, во втором диагональ смещена на 1 от основной и так далее.
Например, в синтаксисе MATLAB:
A = [1, 2, 3
4, 5, 6
7, 8, 9]
а также
B = [1, 2, 3
5, 6, 4
9, 7, 8]
Редактировать: Кажется, что решение чистой линейной алгебры не существует. Так что я буду более точным о том, что я пытался сделать:
Для некоторого вектора v
размера 1 x m
, Затем определите C = repmat(v,m,1)
, Моя матрица A = C-C.';
, Следовательно, A
по сути все различия ценностей в v
но меня интересует только разница до некоторого расстояния между значениями. Это диагонали A
; но m
настолько велика, что конструкция такого m x m
Матрицы вызывают проблемы нехватки памяти. Я ищу способ извлечь эти диагонали настолько эффективным способом, насколько это возможно (в MATLAB).
Спасибо!
2 ответа
Если вы на самом деле не ищете решение линейной алгебры, то я бы сказал, что построение трех дополнительных матриц того же размера, что и A
использование двух матричных умножений очень неэффективно как во времени, так и в пространстве. Я не уверен, что даже возможно найти матричное решение, учитывая мои ограниченные знания линейной алгебры, но даже если это так, это наверняка будет грязно.
Поскольку вы говорите, что вам нужны значения только для некоторых диагоналей, я построю только эти диагонали, используя diag
:
A = [1 2 3;
4 5 6;
7 8 9];
m = size(A, 1); % assume A is square
k = 1; % let's get the k'th diagonal
kdiag = [diag(A, k); diag(A, k-m)];
kdiag =
2
6
7
Диагональ 0
главная диагональ, диагональ m-1
(для mxm
матрица) является последней. Так что, если вы хотели все B
Вы можете легко зациклить:
B = zeros(size(A));
for k = 0:m-1
B(:,k+1) = [diag(A, k); diag(A, k-m)];
end
B =
1 2 3
5 6 4
9 7 8
Из комментариев:
Для v некоторый вектор размером 1xm. Тогда B=repmat(v,m,1). Моя матрица A=BB.'; A - это, по сути, все различия значений в v, но меня интересует только разница до некоторого расстояния между значениями.
Скажем
m = 4;
v = [1 3 7 11];
Если вы построите всю матрицу,
B = repmat(v, m, 1);
A = B - B.';
A =
0 2 6 10
-2 0 4 8
-6 -4 0 4
-10 -8 -4 0
Основная диагональ - нули, так что это не очень интересно. Следующая диагональ, которую я назову k = 1
является
[2 4 4 -10].'
Вы можете построить эту диагональ без построения A
или даже B
сдвигая элементы v
:
k = 1;
diag1 = circshift(v, m-k, 2) - v;
diag1 =
2 4 4 -10
Основная диагональ задается k = 0
последняя диагональ k = m-1
,
Вы можете сделать это с помощью функции toeplitz
создать индексы столбцов для перестановки, а затем преобразовать их в линейный индекс, чтобы использовать для переупорядочения A
, вот так:
>> A = [1 2 3; 4 5 6; 7 8 9]
A =
1 2 3
4 5 6
7 8 9
>> n = size(A, 1);
>> index = repmat((1:n).', 1, n)+n*(toeplitz([1 n:-1:2], 1:n)-1);
>> B = zeros(n);
>> B(index) = A
B =
1 2 3
5 6 4
9 7 8
Это будет обобщать на любой размер квадратной матрицы A
,