mirror of
https://github.com/gonum/gonum.git
synced 2025-10-06 07:37:03 +08:00
mat: add IsZero method to resetable types
This commit is contained in:
@@ -475,5 +475,5 @@ func (c *Cholesky) isZero() bool {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (c *Cholesky) valid() bool {
|
func (c *Cholesky) valid() bool {
|
||||||
return !c.isZero() && !c.chol.isZero()
|
return !c.isZero() && !c.chol.IsZero()
|
||||||
}
|
}
|
||||||
|
@@ -69,7 +69,7 @@ func (m *Dense) reuseAs(r, c int) {
|
|||||||
// Panic as a string, not a mat.Error.
|
// Panic as a string, not a mat.Error.
|
||||||
panic("mat: caps not correctly set")
|
panic("mat: caps not correctly set")
|
||||||
}
|
}
|
||||||
if m.isZero() {
|
if m.IsZero() {
|
||||||
m.mat = blas64.General{
|
m.mat = blas64.General{
|
||||||
Rows: r,
|
Rows: r,
|
||||||
Cols: c,
|
Cols: c,
|
||||||
@@ -95,7 +95,7 @@ func (m *Dense) reuseAsZeroed(r, c int) {
|
|||||||
// Panic as a string, not a mat.Error.
|
// Panic as a string, not a mat.Error.
|
||||||
panic("mat: caps not correctly set")
|
panic("mat: caps not correctly set")
|
||||||
}
|
}
|
||||||
if m.isZero() {
|
if m.IsZero() {
|
||||||
m.mat = blas64.General{
|
m.mat = blas64.General{
|
||||||
Rows: r,
|
Rows: r,
|
||||||
Cols: c,
|
Cols: c,
|
||||||
@@ -147,7 +147,9 @@ func (m *Dense) Reset() {
|
|||||||
m.mat.Data = m.mat.Data[:0]
|
m.mat.Data = m.mat.Data[:0]
|
||||||
}
|
}
|
||||||
|
|
||||||
func (m *Dense) isZero() bool {
|
// IsZero returns whether the receiver is zero-sized. Zero-sized matrices can be the
|
||||||
|
// receiver for size-restricted operations. Dense matrices can be zeroed using Reset.
|
||||||
|
func (m *Dense) IsZero() bool {
|
||||||
// It must be the case that m.Dims() returns
|
// It must be the case that m.Dims() returns
|
||||||
// zeros in this case. See comment in Reset().
|
// zeros in this case. See comment in Reset().
|
||||||
return m.mat.Stride == 0
|
return m.mat.Stride == 0
|
||||||
|
@@ -467,7 +467,7 @@ func (m *Dense) Exp(a Matrix) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
var w *Dense
|
var w *Dense
|
||||||
if m.isZero() {
|
if m.IsZero() {
|
||||||
m.reuseAsZeroed(r, r)
|
m.reuseAsZeroed(r, r)
|
||||||
w = m
|
w = m
|
||||||
} else {
|
} else {
|
||||||
@@ -696,7 +696,7 @@ func (m *Dense) Outer(alpha float64, x, y *Vector) {
|
|||||||
// Panic as a string, not a mat.Error.
|
// Panic as a string, not a mat.Error.
|
||||||
panic("mat: caps not correctly set")
|
panic("mat: caps not correctly set")
|
||||||
}
|
}
|
||||||
if m.isZero() {
|
if m.IsZero() {
|
||||||
m.mat = blas64.General{
|
m.mat = blas64.General{
|
||||||
Rows: r,
|
Rows: r,
|
||||||
Cols: c,
|
Cols: c,
|
||||||
|
17
mat/doc.go
17
mat/doc.go
@@ -36,10 +36,23 @@
|
|||||||
// zero.Copy(a)
|
// zero.Copy(a)
|
||||||
//
|
//
|
||||||
// Receivers must be the correct size for the matrix operations, otherwise the
|
// Receivers must be the correct size for the matrix operations, otherwise the
|
||||||
// operation will panic. As a special case for convenience, a zero-sized matrix
|
// operation will panic. As a special case for convenience, a zero-value matrix
|
||||||
// will be modified to have the correct size, allocating data if necessary.
|
// will be modified to have the correct size, allocating data if necessary.
|
||||||
// var c mat.Dense // construct a new zero-sized matrix
|
// var c mat.Dense // construct a new zero-sized matrix
|
||||||
// c.Mul(a, a) // c is automatically adjusted to be 6×6
|
// c.Mul(a, a) // c is automatically adjusted to be 6×6
|
||||||
|
//
|
||||||
|
// Zero-value of a matrix
|
||||||
|
//
|
||||||
|
// A zero-value matrix is either the Go language definition of a zero-value or
|
||||||
|
// is a zero-sized matrix with zero-length stride. Matrix implementations may have
|
||||||
|
// a Reset method to revert the receiver into a zero-valued matrix and an IsZero
|
||||||
|
// method that returns whether the matrix is zero-valued.
|
||||||
|
// So the following will all result in a zero-value matrix.
|
||||||
|
// - var a mat.Dense
|
||||||
|
// - a := NewDense(0, 0, make([]float64, 0, 100))
|
||||||
|
// - a.Reset()
|
||||||
|
// A zero-value matrix can not be sliced even if it does have an adequately sized
|
||||||
|
// backing data slice, but can be expanded using its Grow method if it exists.
|
||||||
//
|
//
|
||||||
// The Matrix Interfaces
|
// The Matrix Interfaces
|
||||||
//
|
//
|
||||||
|
@@ -109,7 +109,7 @@ func (m Dense) MarshalBinaryTo(w io.Writer) (int, error) {
|
|||||||
// UnmarshalBinary does not limit the size of the unmarshaled matrix, and so
|
// UnmarshalBinary does not limit the size of the unmarshaled matrix, and so
|
||||||
// it should not be used on untrusted data.
|
// it should not be used on untrusted data.
|
||||||
func (m *Dense) UnmarshalBinary(data []byte) error {
|
func (m *Dense) UnmarshalBinary(data []byte) error {
|
||||||
if !m.isZero() {
|
if !m.IsZero() {
|
||||||
panic("mat: unmarshal into non-zero matrix")
|
panic("mat: unmarshal into non-zero matrix")
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -158,7 +158,7 @@ func (m *Dense) UnmarshalBinary(data []byte) error {
|
|||||||
// UnmarshalBinary does not limit the size of the unmarshaled matrix, and so
|
// UnmarshalBinary does not limit the size of the unmarshaled matrix, and so
|
||||||
// it should not be used on untrusted data.
|
// it should not be used on untrusted data.
|
||||||
func (m *Dense) UnmarshalBinaryFrom(r io.Reader) (int, error) {
|
func (m *Dense) UnmarshalBinaryFrom(r io.Reader) (int, error) {
|
||||||
if !m.isZero() {
|
if !m.IsZero() {
|
||||||
panic("mat: unmarshal into non-zero matrix")
|
panic("mat: unmarshal into non-zero matrix")
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -268,7 +268,7 @@ func (v Vector) MarshalBinaryTo(w io.Writer) (int, error) {
|
|||||||
// UnmarshalBinary does not limit the size of the unmarshaled vector, and so
|
// UnmarshalBinary does not limit the size of the unmarshaled vector, and so
|
||||||
// it should not be used on untrusted data.
|
// it should not be used on untrusted data.
|
||||||
func (v *Vector) UnmarshalBinary(data []byte) error {
|
func (v *Vector) UnmarshalBinary(data []byte) error {
|
||||||
if !v.isZero() {
|
if !v.IsZero() {
|
||||||
panic("mat: unmarshal into non-zero vector")
|
panic("mat: unmarshal into non-zero vector")
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -301,7 +301,7 @@ func (v *Vector) UnmarshalBinary(data []byte) error {
|
|||||||
// See MarshalBinary for the on-disk layout.
|
// See MarshalBinary for the on-disk layout.
|
||||||
// See UnmarshalBinary for the list of sanity checks performed on the input.
|
// See UnmarshalBinary for the list of sanity checks performed on the input.
|
||||||
func (v *Vector) UnmarshalBinaryFrom(r io.Reader) (int, error) {
|
func (v *Vector) UnmarshalBinaryFrom(r io.Reader) (int, error) {
|
||||||
if !v.isZero() {
|
if !v.IsZero() {
|
||||||
panic("mat: unmarshal into non-zero vector")
|
panic("mat: unmarshal into non-zero vector")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -71,7 +71,7 @@ func newMultiplier(m *Dense, factors []Matrix) *multiplier {
|
|||||||
// allocate data for m.
|
// allocate data for m.
|
||||||
r, c := m.Dims()
|
r, c := m.Dims()
|
||||||
fr, fc := factors[0].Dims() // newMultiplier is only called with len(factors) > 2.
|
fr, fc := factors[0].Dims() // newMultiplier is only called with len(factors) > 2.
|
||||||
if !m.isZero() {
|
if !m.IsZero() {
|
||||||
if fr != r {
|
if fr != r {
|
||||||
panic(ErrShape)
|
panic(ErrShape)
|
||||||
}
|
}
|
||||||
|
@@ -126,7 +126,9 @@ func (s *SymDense) Reset() {
|
|||||||
s.mat.Data = s.mat.Data[:0]
|
s.mat.Data = s.mat.Data[:0]
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *SymDense) isZero() bool {
|
// IsZero returns whether the receiver is zero-sized. Zero-sized matrices can be the
|
||||||
|
// receiver for size-restricted operations. SymDense matrices can be zeroed using Reset.
|
||||||
|
func (s *SymDense) IsZero() bool {
|
||||||
// It must be the case that m.Dims() returns
|
// It must be the case that m.Dims() returns
|
||||||
// zeros in this case. See comment in Reset().
|
// zeros in this case. See comment in Reset().
|
||||||
return s.mat.N == 0
|
return s.mat.N == 0
|
||||||
@@ -138,7 +140,7 @@ func (s *SymDense) reuseAs(n int) {
|
|||||||
if s.mat.N > s.cap {
|
if s.mat.N > s.cap {
|
||||||
panic(badSymCap)
|
panic(badSymCap)
|
||||||
}
|
}
|
||||||
if s.isZero() {
|
if s.IsZero() {
|
||||||
s.mat = blas64.Symmetric{
|
s.mat = blas64.Symmetric{
|
||||||
N: n,
|
N: n,
|
||||||
Stride: n,
|
Stride: n,
|
||||||
@@ -283,7 +285,7 @@ func (s *SymDense) SymRankK(a Symmetric, alpha float64, x Matrix) {
|
|||||||
func (s *SymDense) SymOuterK(alpha float64, x Matrix) {
|
func (s *SymDense) SymOuterK(alpha float64, x Matrix) {
|
||||||
n, _ := x.Dims()
|
n, _ := x.Dims()
|
||||||
switch {
|
switch {
|
||||||
case s.isZero():
|
case s.IsZero():
|
||||||
s.mat = blas64.Symmetric{
|
s.mat = blas64.Symmetric{
|
||||||
N: n,
|
N: n,
|
||||||
Stride: n,
|
Stride: n,
|
||||||
|
@@ -135,7 +135,7 @@ func (t *TriDense) Dims() (r, c int) {
|
|||||||
// Triangle returns the dimension of t and its orientation. The returned
|
// Triangle returns the dimension of t and its orientation. The returned
|
||||||
// orientation is only valid when n is not zero.
|
// orientation is only valid when n is not zero.
|
||||||
func (t *TriDense) Triangle() (n int, kind TriKind) {
|
func (t *TriDense) Triangle() (n int, kind TriKind) {
|
||||||
return t.mat.N, TriKind(!t.isZero()) && t.triKind()
|
return t.mat.N, TriKind(!t.IsZero()) && t.triKind()
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *TriDense) isUpper() bool {
|
func (t *TriDense) isUpper() bool {
|
||||||
@@ -200,7 +200,9 @@ func (t *TriDense) Reset() {
|
|||||||
t.mat.Data = t.mat.Data[:0]
|
t.mat.Data = t.mat.Data[:0]
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *TriDense) isZero() bool {
|
// IsZero returns whether the receiver is zero-sized. Zero-sized matrices can be the
|
||||||
|
// receiver for size-restricted operations. TriDense matrices can be zeroed using Reset.
|
||||||
|
func (t *TriDense) IsZero() bool {
|
||||||
// It must be the case that t.Dims() returns
|
// It must be the case that t.Dims() returns
|
||||||
// zeros in this case. See comment in Reset().
|
// zeros in this case. See comment in Reset().
|
||||||
return t.mat.Stride == 0
|
return t.mat.Stride == 0
|
||||||
@@ -227,7 +229,7 @@ func (t *TriDense) reuseAs(n int, kind TriKind) {
|
|||||||
if t.mat.N > t.cap {
|
if t.mat.N > t.cap {
|
||||||
panic(badTriCap)
|
panic(badTriCap)
|
||||||
}
|
}
|
||||||
if t.isZero() {
|
if t.IsZero() {
|
||||||
t.mat = blas64.Triangular{
|
t.mat = blas64.Triangular{
|
||||||
N: n,
|
N: n,
|
||||||
Stride: n,
|
Stride: n,
|
||||||
|
@@ -67,7 +67,7 @@ func (v *Vector) SliceVec(i, k int) *Vector {
|
|||||||
// Dims returns the number of rows and columns in the matrix. Columns is always 1
|
// Dims returns the number of rows and columns in the matrix. Columns is always 1
|
||||||
// for a non-Reset vector.
|
// for a non-Reset vector.
|
||||||
func (v *Vector) Dims() (r, c int) {
|
func (v *Vector) Dims() (r, c int) {
|
||||||
if v.isZero() {
|
if v.IsZero() {
|
||||||
return 0, 0
|
return 0, 0
|
||||||
}
|
}
|
||||||
return v.n, 1
|
return v.n, 1
|
||||||
@@ -76,7 +76,7 @@ func (v *Vector) Dims() (r, c int) {
|
|||||||
// Caps returns the number of rows and columns in the backing matrix. Columns is always 1
|
// Caps returns the number of rows and columns in the backing matrix. Columns is always 1
|
||||||
// for a non-Reset vector.
|
// for a non-Reset vector.
|
||||||
func (v *Vector) Caps() (r, c int) {
|
func (v *Vector) Caps() (r, c int) {
|
||||||
if v.isZero() {
|
if v.IsZero() {
|
||||||
return 0, 0
|
return 0, 0
|
||||||
}
|
}
|
||||||
return v.Cap(), 1
|
return v.Cap(), 1
|
||||||
@@ -89,7 +89,7 @@ func (v *Vector) Len() int {
|
|||||||
|
|
||||||
// Cap returns the capacity of the vector.
|
// Cap returns the capacity of the vector.
|
||||||
func (v *Vector) Cap() int {
|
func (v *Vector) Cap() int {
|
||||||
if v.isZero() {
|
if v.IsZero() {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
return (cap(v.mat.Data)-1)/v.mat.Inc + 1
|
return (cap(v.mat.Data)-1)/v.mat.Inc + 1
|
||||||
@@ -426,7 +426,7 @@ func (v *Vector) MulVec(a Matrix, b *Vector) {
|
|||||||
// reuseAs resizes an empty vector to a r×1 vector,
|
// reuseAs resizes an empty vector to a r×1 vector,
|
||||||
// or checks that a non-empty matrix is r×1.
|
// or checks that a non-empty matrix is r×1.
|
||||||
func (v *Vector) reuseAs(r int) {
|
func (v *Vector) reuseAs(r int) {
|
||||||
if v.isZero() {
|
if v.IsZero() {
|
||||||
v.mat = blas64.Vector{
|
v.mat = blas64.Vector{
|
||||||
Inc: 1,
|
Inc: 1,
|
||||||
Data: use(v.mat.Data, r),
|
Data: use(v.mat.Data, r),
|
||||||
@@ -439,7 +439,9 @@ func (v *Vector) reuseAs(r int) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Vector) isZero() bool {
|
// IsZero returns whether the receiver is zero-sized. Zero-sized vectors can be the
|
||||||
|
// receiver for size-restricted operations. Vectors can be zeroed using Reset.
|
||||||
|
func (v *Vector) IsZero() bool {
|
||||||
// It must be the case that v.Dims() returns
|
// It must be the case that v.Dims() returns
|
||||||
// zeros in this case. See comment in Reset().
|
// zeros in this case. See comment in Reset().
|
||||||
return v.mat.Inc == 0
|
return v.mat.Inc == 0
|
||||||
|
Reference in New Issue
Block a user