У меня есть n
переменные действительного числа (не знаю, на самом деле все равно), давайте назовем их X[n]
.У меня также есть m >> n
отношения между ними, назовем их R[m]
, в форме:
X[i] = alpha*X[j]
, alpha
- ненулевое положительное действительное число, i
и j
различны, нопара (i, j)
не обязательно уникальна (т. е. между одними и теми же переменными может быть два отношения с разным альфа-фактором)
Я пытаюсь найти набор alpha
параметров, которые решаютпереопределенная система в некотором смысле наименьших квадратов.Идеальным решением было бы минимизировать возведенную в квадрат сумму разностей между каждым параметром уравнения и его выбранным значением, но меня устраивает следующее приближение:
Если я превращу m уравнений в переопределенную систему из n неизвестныхлюбой псевдообратный числовой решатель даст мне очевидное решение (все нули).Итак, в настоящее время я добавляю еще одно уравнение в микс x[0] = 1
(на самом деле подойдет любая константа) и решает сгенерированную систему в смысле наименьших квадратов, используя псевдообрат Мура-Пенроуза.Хотя это пытается минимизировать сумму (x[0] - 1)^2
и квадратную сумму x[i] - alpha*x[j]
, я считаю это хорошим и численно устойчивым приближением к моей проблеме.Вот пример:
a = 1
a = 2*b
b = 3*c
a = 5*c
в октаве:
A = [
1 0 0;
1 -2 0;
0 1 -3;
1 0 -5;
]
B = [1; 0; 0; 0]
C = pinv(A) * B or better yet:
C = pinv(A)(:,1)
, который дает значения для a
, b
, c
: [0.99383; 0.51235; 0.19136]
, который дает мнеследующие (разумные) отношения:
a = 1.9398*b
b = 2.6774*c
a = 5.1935*c
Так что сейчас мне нужно реализовать это в C / C ++ / Java, и у меня есть следующие вопросы:
Есть ли более быстрый способ решениямоя проблема, или я на правильном пути с созданием переопределенной системы и вычислением псевдообратного?
Мое текущее решение требует разложения по сингулярному значению и трех умножений матриц, что немного с учетом m
может быть 5000 или даже 10000. Существуют ли более быстрые способы вычисления псевдообратного (на самом деле, мне нужен только первый столбец этого столбца, а не вся матрица, учитывая, что B равен нулю, кроме первой строки), учитывая разреженность матрицы(каждая строка содержит ровно два ненулевых значения, одно из которых всегда одно, а другое всегда отрицательное)
Какие математические библиотеки вы бы предложили использоватьза это?Лапак в порядке?
Я также открыт для любых других предложений, при условии, что они численно устойчивы и асимптотически бывают быстрыми (скажем, k*n^2
, где k
может быть большим).