У меня есть:
dataA := []complex128{
1 + 2i, 3 + 4i,
5 + 6i, 7 + 8i,
}
A := mat.NewCDense(2, 2, dataA)
dataB := []complex128{
9 + 10i, 11 + 12i,
13 + 14i, 15 + 16i,
}
B := mat.NewCDense(2, 2, dataB)
var C mat.CDense
C.Mul(A, B)
это не работает
type mat.CDense has no field or method Mul)
как умножать комплексные матрицы Golang gonum/mat
🤔 А знаете ли вы, что...
Go обладает мощным статическим анализатором кода.
Умножение сложных матриц не реализовано в gonum
. Идет закрытый пиар, с реализацией Mul
на CMatrix
. Пиар был закрыт по причине «потому что [пиар] устарел. Мы все еще заинтересованы в пожертвованиях»
Реализация из пиара от notmgsk:
func (m *CDense) Mul(a, b CMatrix) {
ar, ac := a.Dims()
br, bc := b.Dims()
if ac != br {
panic(ErrShape)
}
aU, aTrans, aConj := untransposeCmplx(a)
bU, bTrans, bConj := untransposeCmplx(b)
m.reuseAsNonZeroed(ar, bc)
var restore func()
if aTrans != aConj && m == aU {
m, restore = m.isolatedWorkspace(aU)
defer restore()
} else if bTrans != bConj && m == bU {
m, restore = m.isolatedWorkspace(bU)
defer restore()
}
aT := blas.NoTrans
if aTrans {
aT = blas.Trans
} else if aConj {
aT = blas.ConjTrans
}
bT := blas.NoTrans
if bTrans != bConj {
bT = blas.Trans
} else if bConj {
bT = blas.ConjTrans
}
if aU, ok := aU.(*CDense); ok {
switch bU := bU.(type) {
case *CDense:
if restore == nil {
m.checkOverlap(bU.mat)
}
cblas128.Gemm(aT, bT, 1, aU.mat, bU.mat, 0, m.mat)
return
}
}
m.checkOverlapMatrix(aU)
m.checkOverlapMatrix(bU)
row := getZs(ac, false)
defer putZs(row)
for r := 0; r < ar; r++ {
for i := range row {
row[i] = a.At(r, i)
}
for c := 0; c < bc; c++ {
var v complex128
for i, e := range row {
v += e * b.At(i, c)
}
m.mat.Data[r*m.mat.Stride+c] = v
}
}
}
Я смог умножить комплексные матрицы следующим образом:
package main
import (
"fmt"
"gonum.org/v1/gonum/blas"
"gonum.org/v1/gonum/blas/cblas64"
)
func main() {
a := cblas64.General{
Rows: 2,
Cols: 2,
Stride: 2,
Data: []complex64{1 + 2i, 3 + 4i, 5 + 6i, 7 + 8i},
}
b := cblas64.General{
Rows: 2,
Cols: 1,
Stride: 1,
Data: []complex64{9 + 10i, 11 + 12i},
}
c := cblas64.General{
Rows: 2,
Cols: 1,
Stride: 1,
Data: make([]complex64, 2),
}
cblas64.Gemm(blas.NoTrans, blas.NoTrans, 1, a, b, 0, c)
for i := 0; i < c.Rows; i++ {
fmt.Printf("%v\n", c.Data[i])
}
}