Files
goNum/InconsistentLSQ_test.go
Black Ghost 96fccdb6ef update comments
update comments in all of files in convenient to generate package information using `godoc` command or give tips in LiteIDE editor when the cursor keeps resting on a function or method.
2019-03-01 10:10:32 +08:00

94 lines
2.7 KiB
Go
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
// InconsistentLSQ_test
/*
------------------------------------------------------
作者 : Black Ghost
日期 : 2018-12-11
版本 : 0.0.0
------------------------------------------------------
求解矛盾方程组的最小二乘法Least Square Method
理论:
对于矛盾方程组Ax=b
n
Sum aij*xj = bi (i=1, 2, ..., N)
j=1
rank(A) = n (N > n)
则A'Ax=A'b的唯一解为原矛盾方程组的最小二乘解
参考 李信真, 车刚明, 欧阳洁, 等. 计算方法. 西北工业大学
出版社, 2000, pp 130-135.
------------------------------------------------------
输入 :
A 原方程组系数矩阵Nxn
b 原方程组值向量Nx1
输出 :
sol 解向量
err 解出标志false-未解出或达到步数上限;
true-全部解出
------------------------------------------------------
*/
package goNum_test
import (
"testing"
"github.com/chfenger/goNum"
)
// InconsistentLSQ 求解矛盾方程组的最小二乘法Least Square Method
func InconsistentLSQ(A, b goNum.Matrix) (goNum.Matrix, bool) {
/*
求解矛盾方程组的最小二乘法Least Square Method
输入 :
A 原方程组系数矩阵Nxn
b 原方程组值向量Nx1
输出 :
sol 解向量
err 解出标志false-未解出或达到步数上限;
true-全部解出
*/
//判断A和b的行数是否对应
if A.Rows != b.Rows {
panic("Error in goNum.InconsistentLSQ: Rows of A and b are not equal")
}
//求解A'A和A'b
AA := goNum.DotPruduct(A.Transpose(), A)
Ab := goNum.DotPruduct(A.Transpose(), b)
//转换矩阵为切片
Atemp := goNum.Matrix2ToSlices(AA)
btemp := goNum.Matrix1ToSlices(Ab)
if (len(Atemp) != A.Columns) || (len(Atemp[0]) != A.Columns) || (len(btemp) != A.Columns) {
panic("Error in goNum.InconsistentLSQ: Matrix to slices error")
}
//求解x向量采用列主元消去法LEs_ECPE
soltemp, err := goNum.LEs_ECPE(Atemp, btemp)
if err != true {
panic("Error in goNum.InconsistentLSQ: Solve error")
}
//转换切片为矩阵
sol := goNum.Slices1ToMatrix(soltemp)
if sol.Rows != A.Columns {
panic("Error in goNum.InconsistentLSQ: Slice to matrix error")
}
return sol, true
}
func BenchmarkInconsistentLSQ(b *testing.B) {
A32 := goNum.NewMatrix(6, 3, []float64{1.0, 0.0, 0.0,
0.0, 1.0, 0.0,
0.0, 0.0, 1.0,
-1.0, 1.0, 0.0,
0.0, -1.0, 1.0,
-1.0, 0.0, 1.0})
b32 := goNum.NewMatrix(6, 1, []float64{1.0, 2.0, 3.0, 1.0, 2.0, 1.0})
for i := 0; i < b.N; i++ {
goNum.InconsistentLSQ(A32, b32)
}
}