Skip to main content

Matrix

Struct Matrix 

Source
pub struct Matrix { /* private fields */ }
Expand description

A dense matrix of symbolic expressions.

Elements are stored in row-major order as Vec<Vec<Ex>>.

Equality (==) is structural: two matrices are equal when they have the same shape and every pair of entries is the same canonical expression in the same Context. Use equals for a mathematical (simplifying) comparison.

§Examples

use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [1, 2], [3, 4]];
let b = matrix![ctx, [0, 1], [1, 0]];
let c = &a * &b;                      // matrix product
assert_eq!(c, matrix![ctx, [2, 1], [4, 3]]);
assert_eq!(format!("{}", a.det().unwrap()), "-2");
assert_eq!(a[(1, 0)], ctx.int(3));

Implementations§

Source§

impl Matrix

Source

pub fn new(rows: Vec<Vec<Ex>>) -> Result<Self, SymplexError>

Create a matrix from nested Vecs (row-major).

§Errors

Returns SymplexError::InvalidArgument if rows is empty, any row is empty, or rows have inconsistent lengths.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = Matrix::new(vec![vec![ctx.int(1), ctx.int(2)], vec![ctx.int(3), ctx.int(4)]]).unwrap();
assert_eq!(m.shape(), (2, 2));
assert!(Matrix::new(vec![vec![ctx.int(1)], vec![]]).is_err());
Source

pub fn zeros(ctx: &Context, n: usize, m: usize) -> Self

Create an n × m matrix of zeros.

§Panics

Panics if n == 0 or m == 0.

Source

pub fn identity(ctx: &Context, n: usize) -> Self

Create an n × n identity matrix.

§Panics

Panics if n == 0.

Source

pub fn from_fn(n: usize, m: usize, f: impl FnMut(usize, usize) -> Ex) -> Self

Create an n × m matrix from a closure f(i, j).

§Panics

Panics if n == 0 or m == 0.

Source

pub fn row_vector(elems: Vec<Ex>) -> Self

Create a 1×n row vector from a list of elements.

§Panics

Panics if elems is empty.

Source

pub fn col_vector(elems: Vec<Ex>) -> Self

Create an n×1 column vector from a list of elements.

§Panics

Panics if elems is empty.

Source

pub fn diag(entries: &[Ex]) -> Matrix

Create a square diagonal matrix from a slice of diagonal entries.

The accessor returning the diagonal of an existing matrix is diagonal.

§Panics

Panics if entries is empty.

Source

pub fn from_i64(ctx: &Context, rows: &[&[i64]]) -> Result<Matrix, SymplexError>

Create a matrix of integer literals in the given context.

§Errors

Returns SymplexError::InvalidArgument for empty or jagged input.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = Matrix::from_i64(&ctx, &[&[1, 2], &[3, 4]]).unwrap();
assert_eq!(m, matrix![ctx, [1, 2], [3, 4]]);
Source

pub fn block_diag(blocks: &[&Matrix]) -> Result<Matrix, SymplexError>

Block-diagonal matrix built from the given blocks.

Blocks need not be square; the result is (Σ rows) × (Σ cols) with zeros off the block diagonal.

§Errors

Returns SymplexError::InvalidArgument if blocks is empty.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [1]];
let b = matrix![ctx, [2, 3], [4, 5]];
let bd = Matrix::block_diag(&[&a, &b]).unwrap();
assert_eq!(bd, matrix![ctx, [1, 0, 0], [0, 2, 3], [0, 4, 5]]);
Source§

impl Matrix

Source

pub fn nrows(&self) -> usize

Number of rows.

Source

pub fn ncols(&self) -> usize

Number of columns.

Source

pub fn shape(&self) -> (usize, usize)

Shape as (nrows, ncols).

Source

pub fn is_square(&self) -> bool

Is this matrix square?

Source

pub fn get(&self, i: usize, j: usize) -> &Ex

Immutable reference to element (i, j).

§Panics

Panics if i >= nrows or j >= ncols. For a non-panicking alternative, see try_get.

Source

pub fn try_get(&self, i: usize, j: usize) -> Option<&Ex>

Checked immutable reference to element (i, j).

Returns None if i >= nrows or j >= ncols.

Source

pub fn get_mut(&mut self, i: usize, j: usize) -> &mut Ex

Mutable reference to element (i, j).

§Panics

Panics if i >= nrows or j >= ncols.

Source

pub fn set(&mut self, i: usize, j: usize, value: Ex)

Overwrite element (i, j).

§Panics

Panics if i >= nrows or j >= ncols.

Source

pub fn row(&self, i: usize) -> &[Ex]

Immutable reference to row i as a slice.

§Panics

Panics if i >= nrows.

Source

pub fn col(&self, j: usize) -> Vec<Ex>

Column j as an owned Vec<Ex>.

§Panics

Panics if j >= ncols.

Source

pub fn diagonal(&self) -> Vec<Ex>

The main diagonal [a₀₀, a₁₁, …] (length min(nrows, ncols)).

The constructor building a diagonal matrix is diag.

Source

pub fn submatrix(&self, rows: Range<usize>, cols: Range<usize>) -> Matrix

The sub-block with the given row and column ranges.

§Panics

Panics if either range is empty or extends past the matrix bounds, mirroring slice indexing.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [1, 2, 3], [4, 5, 6], [7, 8, 9]];
assert_eq!(m.submatrix(1..3, 0..2), matrix![ctx, [4, 5], [7, 8]]);
Source

pub fn iter(&self) -> impl Iterator<Item = &Ex> + '_

Iterate over all entries in row-major order.

Source

pub fn to_vec(&self) -> Vec<Vec<Ex>>

Clone the entries into nested Vecs (row-major).

Source

pub fn eval_f64(&self) -> Result<Vec<Vec<f64>>, SymplexError>

Evaluate every entry to f64.

§Errors

Propagates the first entry that cannot be evaluated (free symbols, non-real values, …).

Source

pub fn equals(&self, other: &Matrix) -> Option<bool>

Mathematical equality of two matrices (three-valued).

Returns Some(false) for different shapes, Some(true) when every entry difference simplifies to zero, and None if some entry cannot be decided.

Source

pub fn context(&self) -> Context

Returns a Context handle for this matrix’s elements.

Source§

impl Matrix

Source

pub fn transpose(&self) -> Matrix

Transpose: swap rows and columns.

Source

pub fn adjoint(&self) -> Matrix

Conjugate transpose Aᴴ = conj(A)ᵀ.

Uses Ex::conjugate on every entry; for real-valued entries this coincides with transpose.

Source

pub fn add(&self, other: &Matrix) -> Result<Matrix, SymplexError>

Element-wise addition (method form of operator +).

§Errors

Returns SymplexError::InvalidArgument if shapes differ.

Source

pub fn sub(&self, other: &Matrix) -> Result<Matrix, SymplexError>

Element-wise subtraction (method form of operator -).

§Errors

Returns SymplexError::InvalidArgument if shapes differ.

Source

pub fn hadamard(&self, other: &Matrix) -> Result<Matrix, SymplexError>

Element-wise (Hadamard) product.

§Errors

Returns SymplexError::InvalidArgument if shapes differ.

Source

pub fn scale(&self, scalar: &Ex) -> Matrix

Scalar multiplication: multiply every element by scalar.

Source

pub fn matmul(&self, other: &Matrix) -> Result<Matrix, SymplexError>

Matrix multiplication (self * other).

self is n × p and other is p × m; the result is n × m. Each element is computed symbolically: result[i][j] = Σ_k self[i][k] * other[k][j].

§Errors

Returns SymplexError::InvalidArgument if self.ncols != other.nrows.

Source

pub fn trace(&self) -> Result<Ex, SymplexError>

Trace: sum of the diagonal elements.

§Errors

Returns SymplexError::InvalidArgument if the matrix is not square.

Source

pub fn det(&self) -> Result<Ex, SymplexError>

Determinant of a square matrix.

Dispatch strategy:

  • 1×1 → element
  • 2×2 → ad − bc
  • 3×3 → cofactor expansion (hard-coded, fast)
  • n ≥ 4, all entries rational numbers → Bareiss fraction-free elimination (O(n³), exact)
  • n ≥ 4, symbolic entries → Berkowitz’s division-free algorithm (O(n⁴)), which yields a fully expanded polynomial in the entries instead of an unsimplified rational function.
§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let (a, b, c, d) = (ctx.symbol("a"), ctx.symbol("b"), ctx.symbol("c"), ctx.symbol("d"));
let m = Matrix::new(vec![vec![a.clone(), b.clone()], vec![c.clone(), d.clone()]]).unwrap();
assert_eq!(m.det().unwrap(), &a * &d - &b * &c);
Source

pub fn map(&self, f: impl FnMut(&Ex) -> Ex) -> Matrix

Apply a function to every element, producing a new matrix.

Source

pub fn map_indexed(&self, f: impl FnMut(usize, usize, &Ex) -> Ex) -> Matrix

Apply f(i, j, &a_ij) to every element, producing a new matrix.

Source

pub fn minor_matrix( &self, row: usize, col: usize, ) -> Result<Matrix, SymplexError>

The (n−1) × (n−1) matrix obtained by deleting row row and column col.

§Errors

Returns SymplexError::InvalidArgument if the matrix is not square, has dimension ≤ 1, or the indices are out of range.

Source

pub fn minor(&self, row: usize, col: usize) -> Result<Ex, SymplexError>

The minor M_ij = det(minor_matrix(i, j)).

§Errors

Same conditions as minor_matrix.

Source

pub fn cofactor(&self, row: usize, col: usize) -> Result<Ex, SymplexError>

Cofactor C_ij = (−1)^(i+j) · M_ij.

§Errors

Same conditions as minor_matrix.

Source

pub fn adjugate(&self) -> Result<Matrix, SymplexError>

Adjugate matrix (transpose of the cofactor matrix): adj(A)[i][j] = cofactor(A, j, i).

§Errors

Returns SymplexError::InvalidArgument if the matrix is not square.

Source

pub fn inv(&self) -> Result<Matrix, SymplexError>

Matrix inverse.

Uses Gauss–Jordan elimination on [A | I] for matrices whose entries are all rational numbers (exact, O(n³)) and the adjugate formula A⁻¹ = adj(A) / det(A) for symbolic matrices (keeps entries as polynomial / det).

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [2, 1], [1, 1]];
let inv = a.inv().unwrap();
assert_eq!(&a * &inv, Matrix::identity(&ctx, 2));
assert!(matrix![ctx, [1, 2], [2, 4]].inv().is_err());
Source

pub fn solve(&self, b: &Matrix) -> Result<Matrix, SymplexError>

Solve the linear system Ax = b where self is A.

Uses Gauss–Jordan elimination on the augmented matrix [A | b]. Returns the solution as a Matrix (column vector or multi-column for multiple right-hand sides). Each entry is passed through eval() to fold constants.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [2, 1], [1, 3]];
let b = matrix![ctx, [5], [10]];
let x = a.solve(&b).unwrap();
assert_eq!(x, matrix![ctx, [1], [3]]);
Source

pub fn solve_least_squares(&self, b: &Matrix) -> Result<Matrix, SymplexError>

Least-squares solution of Ax ≈ b via the normal equations AᵀA x = Aᵀb.

Requires A to have full column rank (so that AᵀA is invertible).

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
// Fit y = c0 + c1·x through (0,1), (1,2), (2,4): least squares gives c1 = 3/2, c0 = 5/6
let a = matrix![ctx, [1, 0], [1, 1], [1, 2]];
let b = matrix![ctx, [1], [2], [4]];
let x = a.solve_least_squares(&b).unwrap();
assert_eq!(x[(0, 0)], ctx.rational(5, 6));
assert_eq!(x[(1, 0)], ctx.rational(3, 2));
Source

pub fn char_poly_coeffs(&self) -> Result<Vec<Ex>, SymplexError>

Coefficients of the characteristic polynomial det(A − λI) in ascending degree order: [c_0, c_1, …, c_n] with c_0 = det(A) and c_n = (−1)ⁿ.

Computed with Berkowitz’s division-free algorithm, so the coefficients are expanded polynomials in the entries even for fully symbolic matrices.

§Errors

Returns SymplexError::InvalidArgument if the matrix is not square.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [1, 2], [3, 4]];
// det(A − λI) = λ² − 5λ − 2
let c = a.char_poly_coeffs().unwrap();
assert_eq!(c, vec![ctx.int(-2), ctx.int(-5), ctx.int(1)]);
Source

pub fn char_poly(&self, var: &Ex) -> Result<Ex, SymplexError>

Characteristic polynomial det(A − λI) as a polynomial in var.

This is the one eigen-related method that takes a caller-supplied variable, because the result is a polynomial in that variable. char_poly(λ) evaluated at λ = 0 is det(A).

§Errors

Returns SymplexError::InvalidArgument if the matrix is not square.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let lam = ctx.symbol("lambda");
let a = matrix![ctx, [2, 1], [1, 2]];
let p = a.char_poly(&lam).unwrap();
assert_eq!(p, &lam.powi(2) - &lam * 4 + 3);
Source

pub fn eigenvals_with_multiplicity( &self, ) -> Result<Vec<(Ex, usize)>, SymplexError>

Eigenvalues with algebraic multiplicities: [(λ, multiplicity), …].

The characteristic polynomial is factored over ℤ (exact multiplicities); each irreducible factor is then solved. Rational and quadratic roots are returned in closed form. Irreducible cubic/quartic factors are solved in radicals only when the result is compact (binomial-like after depressing, e.g. λ³ − 2 or λ⁴ − 10λ² + 1); otherwise — and always for degree ≥ 5 — the roots are exact RootOf expressions whose bound variable displays as λ and which evaluate numerically via eval_f64/eval_complex64. (The general Cardano/Ferrari formulas produce nested complex cube roots that make eigenvectors and P⁻¹ swell exponentially.) For 1×1 and 2×2 matrices with symbolic entries the closed-form (quadratic) formula is used.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
// Symmetric with an irreducible cubic characteristic polynomial.
let m = matrix![ctx, [4, 1, 2], [1, 3, 1], [2, 1, 5]];
let ev = m.eigenvals_with_multiplicity().unwrap();
assert_eq!(ev.len(), 3);
assert!(ev.iter().all(|(v, m)| *m == 1 && v.to_string().starts_with("RootOf")));
let sum: f64 = ev.iter().map(|(v, _)| v.eval_f64().unwrap()).sum();
assert!((sum - 12.0).abs() < 1e-9); // Σλ = tr(A)

If the solver cannot find every root, the multiplicities sum to less than n and a warning is logged.

§Errors
Source

pub fn eigenvals(&self) -> Result<Vec<Ex>, SymplexError>

Eigenvalues, repeated according to algebraic multiplicity.

For an n × n matrix whose characteristic polynomial the solver can fully handle this list has exactly n entries. See eigenvals_with_multiplicity for the grouped form and for the handling of unsolvable factors.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [2, 1], [1, 2]];
let mut ev: Vec<String> = a.eigenvals().unwrap().iter().map(|e| e.to_string()).collect();
ev.sort();
assert_eq!(ev, ["1", "3"]);

// Symbolic 2×2: closed form via the quadratic formula
let (a, b) = (ctx.symbol("a"), ctx.symbol("b"));
let m = Matrix::new(vec![vec![a.clone(), b.clone()], vec![b.clone(), a.clone()]]).unwrap();
let ev = m.eigenvals().unwrap();
assert_eq!(ev.len(), 2);
Source

pub fn eigenvects(&self) -> Result<Vec<(Ex, usize, Vec<Matrix>)>, SymplexError>

Eigenvectors: for each eigenvalue, a basis for its eigenspace.

Returns a list of (eigenvalue, algebraic_multiplicity, eigenvectors) tuples. Each eigenvector is a column-vector Matrix; the number of vectors is the geometric multiplicity.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [2, 1], [0, 3]];
for (val, mult, vecs) in m.eigenvects().unwrap() {
    assert_eq!(mult, 1);
    assert_eq!(vecs.len(), 1);
    // A·v = λ·v
    assert_eq!((&m * &vecs[0]).simplify(), vecs[0].scale(&val).simplify());
}
Source

pub fn is_diagonalizable(&self) -> Option<bool>

Is the matrix diagonalizable (three-valued)?

  • Some(true) — every eigenvalue’s geometric multiplicity equals its algebraic multiplicity.
  • Some(false) — non-square, or some eigenvalue is defective (decided only for matrices without free symbols).
  • None — the eigenvalue solver could not find all eigenvalues, or the entries are symbolic and an eigenspace dimension could not be established.
§Examples
use symplex::prelude::*;

let ctx = Context::new();
assert_eq!(matrix![ctx, [1, 0], [0, 2]].is_diagonalizable(), Some(true));
assert_eq!(matrix![ctx, [1, 1], [0, 1]].is_diagonalizable(), Some(false));
Source

pub fn diagonalize(&self) -> Result<(Matrix, Matrix), SymplexError>

Diagonalize: find invertible P and diagonal D with A = P D P⁻¹.

P has the eigenvectors as columns; D carries the eigenvalues in the same order.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [2, 1], [0, 3]];
let (p, d) = m.diagonalize().unwrap();
let back = (&(&p * &d) * &p.inv().unwrap()).simplify();
assert_eq!(back, m);
Source

pub fn jordan_form(&self) -> Result<(Matrix, Matrix), SymplexError>

Jordan normal form: P and block-diagonal J such that A = P J P⁻¹.

J consists of Jordan blocks J_k(λ) (eigenvalue on the diagonal, ones on the superdiagonal); P holds the (generalized) eigenvectors. For diagonalizable matrices this equals diagonalize.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
// Defective: eigenvalue 2 with algebraic mult 2, geometric mult 1
let m = matrix![ctx, [2, 1, 0, 0], [0, 2, 0, 0], [0, 0, 3, 0], [0, 0, 0, 4]];
let (p, j) = m.jordan_form().unwrap();
assert_eq!((&(&p * &j) * &p.inv().unwrap()).simplify(), m);
Source

pub fn powi(&self, n: u32) -> Result<Matrix, SymplexError>

Integer power of a square matrix via repeated squaring.

powi(0) is the identity. Negative powers are not supported — use inv()?.powi(k).

§Errors

Returns SymplexError::InvalidArgument if the matrix is not square.

Source

pub fn kronecker(&self, other: &Matrix) -> Matrix

Kronecker (tensor) product A ⊗ B.

For A (m×n) and B (p×q), produces an (mp×nq) matrix.

Source

pub fn exp_series(&self, order: usize) -> Result<Matrix, SymplexError>

Matrix exponential via truncated Taylor series eᴬ ≈ Σₖ₌₀ⁿ Aᵏ/k!.

This is an approximation. For exact results use matrix_exp.

§Errors

Returns SymplexError::InvalidArgument if the matrix is not square.

Source

pub fn matrix_exp(&self) -> Result<Matrix, SymplexError>

Exact matrix exponential eᴬ via the Jordan decomposition eᴬ = P · e^J · P⁻¹.

For each Jordan block J_k(λ):

e^{J_k(λ)} = e^λ · [ 1,  1,  1/2!, …, 1/(k−1)! ]
                   [ 0,  1,  1,    …, 1/(k−2)! ]
                   [ …                        ]

Unlike a numerical library this never falls back to a series approximation; use exp_series explicitly if an approximation is acceptable.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [0, 1], [-1, 0]];
let e = m.matrix_exp().unwrap();
// e^A = [[cos 1, sin 1], [−sin 1, cos 1]]: complex-conjugate eigenvalue
// pairs are rewritten with Euler's formula, so the entries are real trig.
assert_eq!(e[(0, 0)], ctx.one().cos());
assert_eq!(e[(0, 1)], ctx.one().sin());
Source

pub fn matrix_exp_t(&self, t: &Ex) -> Result<Matrix, SymplexError>

Exact matrix exponential e^{At} for a scalar t.

Equivalent to self.scale(t).matrix_exp() but keeps t out of the eigenvalue computation, so it works for any t (including symbols) whenever matrix_exp works for A. For each Jordan block the entries are e^{λt} · t^{j−i} / (j−i)!.

§Errors

Same conditions as matrix_exp.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let t = ctx.symbol("t");
let a = matrix![ctx, [0, 1], [0, 0]];
let e = a.matrix_exp_t(&t).unwrap();
assert_eq!(e, Matrix::new(vec![vec![ctx.int(1), t.clone()], vec![ctx.int(0), ctx.int(1)]]).unwrap());
Source

pub fn pinv(&self) -> Result<Matrix, SymplexError>

Moore–Penrose pseudo-inverse via A⁺ = (AᵀA)⁻¹Aᵀ.

Valid for full-column-rank matrices.

§Errors

Returns SymplexError::ComputationFailed if AᵀA is singular (the matrix does not have full column rank).

Source§

impl Matrix

Source

pub fn diff(&self, var: &Ex) -> Matrix

Differentiate every element with respect to var.

Source

pub fn integrate(&self, var: &Ex) -> Matrix

Integrate every element with respect to var (indefinite).

Source

pub fn subs(&self, old: &Ex, new: &Ex) -> Matrix

Substitute oldnew in every element.

Source

pub fn eval(&self) -> Matrix

Evaluate every element (constant-fold where possible).

Source

pub fn expand(&self) -> Matrix

Expand every element (distribute products over sums).

Source

pub fn simplify(&self) -> Matrix

Simplify every element via built-in rewrite rules.

Source§

impl Matrix

Source

pub fn to_rust_fn( &self, name: &str, params: &[&str], ) -> Result<String, SymplexError>

Generate a Rust function that computes this matrix and returns a flat array.

Uses cross-entry common subexpression elimination for optimal performance.

§Examples
use symplex::prelude::*;
use symplex::matrix::Matrix;

let ctx = Context::new();
let x = ctx.symbol("x");
let m = Matrix::new(vec![
    vec![x.sin(), x.cos()],
    vec![-x.cos(), x.sin()],
]).unwrap();
let code = m.to_rust_fn("rotation", &["x"]).unwrap();
assert!(code.contains("pub fn rotation"));
assert!(code.contains("[f64; 4]"));
Source

pub fn to_rust_fn_with_options( &self, name: &str, params: &[&str], options: &CodegenOptions, ) -> Result<String, SymplexError>

Generate a Rust function with custom code generation options.

See CodegenOptions for available settings (precision, math backend, annotations, CSE toggle).

Source§

impl Matrix

Source

pub fn to_latex(&self) -> String

Render this matrix as a LaTeX bmatrix.

§Example
use symplex::prelude::*;
let ctx = Context::new();
let m = matrix![ctx, [1, 2], [3, 4]];
assert!(m.to_latex().contains(r"\begin{bmatrix}"));
Source§

impl Matrix

Source

pub fn lu(&self) -> Result<(Matrix, Matrix, Vec<usize>), SymplexError>

LU decomposition with partial pivoting: P·A = L·U.

Returns (L, U, perm) where L is unit lower triangular, U is upper triangular and perm is the row permutation (perm[i] is the original index of row i of P·A). Pivots are chosen as the first structurally non-zero entry, so symbolic entries are treated as non-zero.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [4, 3], [6, 3]];
let (l, u, perm) = a.lu().unwrap();
// Rebuild P·A from perm and compare with L·U
let pa = Matrix::new(perm.iter().map(|&i| a.row(i).to_vec()).collect()).unwrap();
assert_eq!((&l * &u).eval(), pa);
assert!(matrix![ctx, [1, 2], [2, 4]].lu().is_err());
Source

pub fn rref(&self) -> (Matrix, Vec<usize>)

Row-reduced echelon form via Gauss–Jordan elimination.

Returns (rref_matrix, pivot_columns). Uses exact arithmetic; pivots are the first structurally non-zero entries, so symbolic entries are always treated as non-zero. (The eigen-family uses a simplifying zero test internally so that irrational eigenvalues still yield eigenvectors.)

Source

pub fn rank(&self) -> usize

Rank of the matrix (number of pivot columns in RREF).

Source

pub fn nullspace(&self) -> Vec<Matrix>

Null space (kernel): basis vectors for Ax = 0, as column vectors.

Empty for a full-column-rank matrix. Uses structural pivoting like rref.

Source

pub fn columnspace(&self) -> Vec<Matrix>

Column space basis: the pivot columns of the original matrix.

Source

pub fn rowspace(&self) -> Vec<Matrix>

Row space basis: the non-zero rows of the RREF, as row vectors.

Source

pub fn left_nullspace(&self) -> Vec<Matrix>

Left null space: basis of { y : yᵀA = 0 } = nullspace(Aᵀ).

Source§

impl Matrix

Source

pub fn norm_frobenius(&self) -> Ex

Frobenius norm ‖A‖_F = √(Σ |a_ij|²).

Entries are treated as real (squared, not |·|²); for complex entries apply adjoint manually.

Source

pub fn norm(&self) -> Ex

Default norm — the Frobenius norm (norm_frobenius).

Source

pub fn hstack(matrices: &[&Matrix]) -> Result<Matrix, SymplexError>

Stack matrices horizontally (side by side).

§Errors

Returns SymplexError::InvalidArgument if matrices is empty or row counts differ.

Source

pub fn vstack(matrices: &[&Matrix]) -> Result<Matrix, SymplexError>

Stack matrices vertically (on top of each other).

§Errors

Returns SymplexError::InvalidArgument if matrices is empty or column counts differ.

Source

pub fn vec(&self) -> Matrix

Vectorization vec(A): stack the columns into a single (mn)×1 column vector.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [1, 2], [3, 4]];
assert_eq!(a.vec(), matrix![ctx, [1], [3], [2], [4]]);
Source§

impl Matrix

Source

pub fn extract( &self, rows: &[usize], cols: &[usize], ) -> Result<Matrix, SymplexError>

The sub-matrix formed by the given rows and columns, in the order listed. Indices may be repeated or reordered.

§Errors

SymplexError::InvalidArgument if either list is empty or contains an out-of-range index.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [1, 2, 3], [4, 5, 6], [7, 8, 9]];
assert_eq!(m.extract(&[2, 0], &[0, 2, 2]).unwrap(), matrix![ctx, [7, 9, 9], [1, 3, 3]]);
assert!(m.extract(&[3], &[0]).is_err());
assert!(m.extract(&[], &[0]).is_err());
Source

pub fn select_rows(&self, rows: &[usize]) -> Result<Matrix, SymplexError>

The rows with the given indices (all columns), in the order listed.

§Errors

SymplexError::InvalidArgument if rows is empty or contains an out-of-range index.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [1, 2], [3, 4], [5, 6]];
assert_eq!(m.select_rows(&[2, 0]).unwrap(), matrix![ctx, [5, 6], [1, 2]]);
Source

pub fn select_cols(&self, cols: &[usize]) -> Result<Matrix, SymplexError>

The columns with the given indices (all rows), in the order listed.

§Errors

SymplexError::InvalidArgument if cols is empty or contains an out-of-range index.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [1, 2, 3], [4, 5, 6]];
assert_eq!(m.select_cols(&[2, 2]).unwrap(), matrix![ctx, [3, 3], [6, 6]]);
Source

pub fn delete_row(&self, i: usize) -> Result<Matrix, SymplexError>

The matrix with row i removed.

§Errors

SymplexError::InvalidArgument if i is out of range or the matrix has a single row (the result would be empty).

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [1, 2], [3, 4], [5, 6]];
assert_eq!(m.delete_row(1).unwrap(), matrix![ctx, [1, 2], [5, 6]]);
assert!(matrix![ctx, [1, 2]].delete_row(0).is_err());
Source

pub fn delete_col(&self, j: usize) -> Result<Matrix, SymplexError>

The matrix with column j removed.

§Errors

SymplexError::InvalidArgument if j is out of range or the matrix has a single column (the result would be empty).

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = matrix![ctx, [1, 2, 3], [4, 5, 6]];
assert_eq!(m.delete_col(0).unwrap(), matrix![ctx, [2, 3], [5, 6]]);
assert!(matrix![ctx, [1], [2]].delete_col(0).is_err());
Source

pub fn is_integer_matrix(&self) -> Option<bool>

Is every entry an integer literal? Three-valued: Some(true) when every entry is an integer literal, Some(false) when some entry is a non-integer numeric literal (1/2), None when some entry is symbolic (a symbol, pi, an unevaluated sum, …).

Entries are inspected as they are — call eval first to constant-fold 2 + 3 into 5.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
assert_eq!(matrix![ctx, [1, -2], [3, 0]].is_integer_matrix(), Some(true));
let half = Matrix::new(vec![vec![ctx.rational(1, 2)]]).unwrap();
assert_eq!(half.is_integer_matrix(), Some(false));
let sym = Matrix::new(vec![vec![ctx.symbol("x")]]).unwrap();
assert_eq!(sym.is_integer_matrix(), None);
Source

pub fn to_rational_rows(&self) -> Option<Vec<Vec<Ratio<BigInt>>>>

The entries as exact rationals, row-major.

Returns None if any entry is not a numeric literal. Entries are inspected as they are — call eval first to fold constant expressions such as 1/2 + 1/3.

§Examples
use symplex::prelude::*;
use num_bigint::BigInt;
use num_rational::Ratio;

let ctx = Context::new();
let m = Matrix::new(vec![vec![ctx.rational(1, 2), ctx.int(3)]]).unwrap();
let rows = m.to_rational_rows().unwrap();
assert_eq!(rows[0][0], Ratio::new(BigInt::from(1), BigInt::from(2)));
assert_eq!(rows[0][1], Ratio::from_integer(BigInt::from(3)));
assert!(Matrix::new(vec![vec![ctx.symbol("x")]]).unwrap().to_rational_rows().is_none());
Source

pub fn to_bigint_rows(&self) -> Option<Vec<Vec<BigInt>>>

The entries as big integers, row-major.

Returns None if any entry is not an integer literal (a fraction, a symbol, an unevaluated expression, …).

§Examples
use symplex::prelude::*;
use num_bigint::BigInt;

let ctx = Context::new();
let rows = matrix![ctx, [1, -2], [3, 4]].to_bigint_rows().unwrap();
assert_eq!(rows[0][1], BigInt::from(-2));
let half = Matrix::new(vec![vec![ctx.rational(1, 2)]]).unwrap();
assert!(half.to_bigint_rows().is_none());
Source

pub fn from_ratio( ctx: &Context, rows: &[Vec<Ratio<BigInt>>], ) -> Result<Matrix, SymplexError>

Create a matrix of exact rational literals.

§Errors

SymplexError::InvalidArgument for empty or jagged input.

§Examples
use symplex::prelude::*;
use num_bigint::BigInt;
use num_rational::Ratio;

let ctx = Context::new();
let q = |n: i64, d: i64| Ratio::new(BigInt::from(n), BigInt::from(d));
let m = Matrix::from_ratio(&ctx, &[vec![q(1, 2), q(3, 1)]]).unwrap();
assert_eq!(m.get(0, 0), &ctx.rational(1, 2));
assert_eq!(m.to_rational_rows().unwrap(), vec![vec![q(1, 2), q(3, 1)]]);
Source

pub fn from_bigint( ctx: &Context, rows: &[Vec<BigInt>], ) -> Result<Matrix, SymplexError>

Create a matrix of integer literals from big integers.

§Errors

SymplexError::InvalidArgument for empty or jagged input.

§Examples
use symplex::prelude::*;
use num_bigint::BigInt;

let ctx = Context::new();
let rows = vec![vec![BigInt::from(1), BigInt::from(2)], vec![BigInt::from(3), BigInt::from(4)]];
let m = Matrix::from_bigint(&ctx, &rows).unwrap();
assert_eq!(m, matrix![ctx, [1, 2], [3, 4]]);
Source

pub fn from_f64_rows( ctx: &Context, rows: &[Vec<f64>], ) -> Result<Matrix, SymplexError>

Create a matrix from f64 values, converting each exactly to the dyadic rational it represents (via Context::from_f64): 0.5 becomes 1/2, but 0.1 becomes 3602879701896397/36028797018963968, not 1/10. Use Context::from_f64_nice entry-wise if you want the “human” rational reading of a float.

§Errors

SymplexError::InvalidArgument for empty or jagged input or a NaN entry.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let m = Matrix::from_f64_rows(&ctx, &[vec![0.5, -3.0], vec![0.25, 2.0]]).unwrap();
assert_eq!(m.get(0, 0), &ctx.rational(1, 2));
assert_eq!(m.get(1, 0), &ctx.rational(1, 4));
assert!(Matrix::from_f64_rows(&ctx, &[vec![f64::NAN]]).is_err());
Source

pub fn subs_map(&self, replacements: &[(&Ex, &Ex)]) -> Matrix

Simultaneous substitution of several (old, new) pairs in every entry (see Ex::subs_map).

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let (x, y) = (ctx.symbol("x"), ctx.symbol("y"));
let m = Matrix::new(vec![vec![x.clone(), y.clone()]]).unwrap();
// Swap x and y in one step — sequential `subs` would collapse both to y.
let swapped = m.subs_map(&[(&x, &y), (&y, &x)]);
assert_eq!(swapped, Matrix::new(vec![vec![y, x]]).unwrap());
Source

pub fn nnz(&self) -> usize

Number of structurally non-zero entries (entries that are not the literal 0). Symbolic entries count as non-zero even if they would simplify to zero.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
assert_eq!(matrix![ctx, [1, 0, 2], [0, 0, 3]].nnz(), 3);
assert_eq!(Matrix::identity(&ctx, 4).nnz(), 4);
Source§

impl Matrix

Source

pub fn hermite_normal_form(&self) -> Result<Matrix, SymplexError>

Row-style Hermite normal form H = U·A of an integer matrix.

See normalforms::hermite_normal_form for the exact normalisation and normalforms::hermite_normal_form_with_transform to obtain U as well.

§Errors

SymplexError::InvalidArgument if any entry is not an integer literal.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [2, 4, 4], [-6, 6, 12], [10, -4, -16]];
let h = a.hermite_normal_form().unwrap();
assert_eq!(h, matrix![ctx, [2, 4, 4], [0, 6, 0], [0, 0, 12]]);
Source

pub fn smith_normal_form(&self) -> Result<Matrix, SymplexError>

Smith normal form S = U·A·V of an integer matrix: a diagonal matrix diag(d₁, …, dᵣ, 0, …) with dᵢ > 0 and dᵢ | dᵢ₊₁.

See normalforms::smith_normal_form and normalforms::smith_normal_form_with_transforms.

§Errors

SymplexError::InvalidArgument if any entry is not an integer literal.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [2, 4, 4], [-6, 6, 12], [10, -4, -16]];
assert_eq!(a.smith_normal_form().unwrap(), matrix![ctx, [2, 0, 0], [0, 6, 0], [0, 0, 12]]);
Source

pub fn integer_nullspace(&self) -> Result<Vec<Matrix>, SymplexError>

A ℤ-basis of the integer kernel {x ∈ ℤⁿ : A·x = 0}, as column vectors (empty when the kernel is trivial).

See normalforms::integer_nullspace.

§Errors

SymplexError::InvalidArgument if any entry is not an integer literal.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [2, 4, 6]];
let basis = a.integer_nullspace().unwrap();
assert_eq!(basis.len(), 2);
for k in &basis {
    assert_eq!((&a * k).eval(), matrix![ctx, [0]]);
}
Source§

impl Matrix

Source

pub fn qr(&self) -> Result<(Matrix, Matrix), SymplexError>

QR decomposition via Gram–Schmidt: A = Q·R with Q (m×n) having orthonormal columns and R (n×n) upper triangular.

Works exactly with radicals (entries like 1/√2). Requires the columns of A to be linearly independent (rank == ncols).

§Errors

Returns SymplexError::ComputationFailed if the columns are linearly dependent or symbolic entries swell beyond EXPRESSION_BUDGET.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [1, 1], [0, 1]];
let (q, r) = a.qr().unwrap();
assert_eq!((&q * &r).simplify(), a);
assert_eq!((&q.transpose() * &q).simplify(), Matrix::identity(&ctx, 2));
assert!(r[(1, 0)].is_zero_structural());
Source

pub fn cholesky(&self) -> Result<Matrix, SymplexError>

Cholesky decomposition A = L·Lᵀ for a symmetric positive-definite matrix (L lower triangular with positive diagonal).

Positive-definiteness is decided pivot by pivot: each diagonal pivot must be provably positive (assumption system, or numeric evaluation for constant entries).

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [4, 2], [2, 3]];
let l = a.cholesky().unwrap();
assert_eq!((&l * &l.transpose()).simplify(), a);
assert!(matrix![ctx, [1, 2], [2, 1]].cholesky().is_err()); // indefinite
Source

pub fn ldl(&self) -> Result<(Matrix, Matrix), SymplexError>

LDLᵀ decomposition A = L·D·Lᵀ for a symmetric matrix (L unit lower triangular, D diagonal).

Unlike cholesky this needs no square roots and no sign information, so it works for symbolic symmetric matrices and for indefinite ones.

§Errors
§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [4, 2], [2, 3]];
let (l, d) = a.ldl().unwrap();
assert_eq!((&(&l * &d) * &l.transpose()).eval(), a);
assert_eq!(d, matrix![ctx, [4, 0], [0, 2]]);
Source

pub fn is_symmetric(&self) -> Option<bool>

Is A = Aᵀ? Three-valued; Some(false) for non-square.

Source

pub fn is_skew_symmetric(&self) -> Option<bool>

Is A = −Aᵀ? Three-valued; Some(false) for non-square.

Source

pub fn is_hermitian(&self) -> Option<bool>

Is A = Aᴴ (conjugate transpose)? Three-valued.

Source

pub fn is_orthogonal(&self) -> Option<bool>

Is AᵀA = I? Three-valued; Some(false) for non-square.

Source

pub fn is_unitary(&self) -> Option<bool>

Is AᴴA = I? Three-valued; Some(false) for non-square.

Source

pub fn is_upper_triangular(&self) -> Option<bool>

Are all entries below the main diagonal zero? Three-valued.

Source

pub fn is_lower_triangular(&self) -> Option<bool>

Are all entries above the main diagonal zero? Three-valued.

Source

pub fn is_diagonal(&self) -> Option<bool>

Are all off-diagonal entries zero? Three-valued (works for rectangular matrices too).

Source

pub fn is_identity(&self) -> Option<bool>

Is this the identity matrix? Three-valued; Some(false) for non-square.

Source

pub fn is_zero(&self) -> Option<bool>

Are all entries zero? Three-valued.

Source

pub fn is_nilpotent(&self) -> Option<bool>

Is Aⁿ = 0 (n = dimension)? Three-valued; Some(false) for non-square.

A square matrix is nilpotent iff Aⁿ = 0, so exactly one matrix power is examined.

Source

pub fn is_positive_definite(&self) -> Option<bool>

Positive-definiteness via Sylvester’s criterion: symmetric and all leading principal minors strictly positive. Three-valued.

Returns Some(false) for non-square or provably non-symmetric matrices and None when a minor’s sign cannot be decided (symbolic entries without assumptions).

§Examples
use symplex::prelude::*;

let ctx = Context::new();
assert_eq!(matrix![ctx, [2, -1], [-1, 2]].is_positive_definite(), Some(true));
assert_eq!(matrix![ctx, [1, 2], [2, 1]].is_positive_definite(), Some(false));
let x = ctx.symbol("x");
let m = Matrix::new(vec![vec![x.clone(), ctx.int(0)], vec![ctx.int(0), ctx.int(1)]]).unwrap();
assert_eq!(m.is_positive_definite(), None);
Source

pub fn is_positive_semidefinite(&self) -> Option<bool>

Positive-semidefiniteness: symmetric and all principal minors non-negative (leading minors alone are not sufficient). Three-valued.

Examines 2ⁿ − 1 minors, so this is intended for small matrices.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
assert_eq!(matrix![ctx, [1, 1], [1, 1]].is_positive_semidefinite(), Some(true));
assert_eq!(matrix![ctx, [0, 0], [0, -1]].is_positive_semidefinite(), Some(false));
Source

pub fn norm_1(&self) -> Ex

Induced 1-norm: maximum absolute column sum.

For symbolic entries the result is a max(…) of abs(…) sums; call .eval() to fold constants.

Source

pub fn norm_inf(&self) -> Ex

Induced ∞-norm: maximum absolute row sum.

Source

pub fn norm_p(&self, p: &Ex) -> Result<Ex, SymplexError>

Vector p-norm (Σ |xᵢ|ᵖ)^(1/p) for a row or column vector.

§Errors

Returns SymplexError::InvalidArgument if the matrix is not a row or column vector.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let v = matrix![ctx, [3], [-4]];
assert_eq!(v.norm_p(&ctx.int(2)).unwrap().eval(), ctx.int(5));
assert_eq!(v.norm_p(&ctx.int(1)).unwrap().eval(), ctx.int(7));
Source

pub fn matrix_pow_symbolic(&self, n: &Ex) -> Result<Matrix, SymplexError>

Symbolic power Aⁿ for a diagonalizable matrix via P·Dⁿ·P⁻¹.

n may be any expression (a symbol, a rational, …); each diagonal entry becomes λᵢⁿ. Entries are simplified.

§Errors

Same conditions as diagonalize.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let n = ctx.symbol("n");
let a = matrix![ctx, [2, 0], [0, 3]];
let an = a.matrix_pow_symbolic(&n).unwrap();
assert_eq!(an[(0, 0)], ctx.int(2).pow(&n));
assert_eq!(an[(1, 1)], ctx.int(3).pow(&n));
Source

pub fn matrix_sqrt(&self) -> Result<Matrix, SymplexError>

Principal square root √A of a diagonalizable matrix via P·√D·P⁻¹ (principal branch on each eigenvalue).

§Errors

Same conditions as diagonalize.

§Examples
use symplex::prelude::*;

let ctx = Context::new();
let a = matrix![ctx, [4, 0], [0, 9]];
let s = a.matrix_sqrt().unwrap();
assert_eq!((&s * &s).simplify(), a);

Trait Implementations§

Source§

impl Add for Matrix

Source§

type Output = Matrix

The resulting type after applying the + operator.
Source§

fn add(self, rhs: Matrix) -> Matrix

Performs the + operation. Read more
Source§

impl Add<&Matrix> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the + operator.
Source§

fn add(self, rhs: &Matrix) -> Matrix

Performs the + operation. Read more
Source§

impl Add<&Matrix> for Matrix

Source§

type Output = Matrix

The resulting type after applying the + operator.
Source§

fn add(self, rhs: &Matrix) -> Matrix

Performs the + operation. Read more
Source§

impl Add<Matrix> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the + operator.
Source§

fn add(self, rhs: Matrix) -> Matrix

Performs the + operation. Read more
Source§

impl Clone for Matrix

Source§

fn clone(&self) -> Matrix

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Debug for Matrix

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Matrix(2×2, [[1, 2], [3, 4]]) — shape followed by the rows inline.

Source§

impl Display for Matrix

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Single-row matrices print inline as [[a, b, c]]; larger matrices print one row per line with columns right-aligned:

[
  [ 1, -2],
  [30,  4]
]
Source§

impl Div<&Expr<Numeric>> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the / operator.
Source§

fn div(self, rhs: &Ex) -> Matrix

Performs the / operation. Read more
Source§

impl Div<&Expr<Numeric>> for Matrix

Source§

type Output = Matrix

The resulting type after applying the / operator.
Source§

fn div(self, rhs: &Ex) -> Matrix

Performs the / operation. Read more
Source§

impl Div<Expr<Numeric>> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the / operator.
Source§

fn div(self, rhs: Ex) -> Matrix

Performs the / operation. Read more
Source§

impl Div<Expr<Numeric>> for Matrix

Source§

type Output = Matrix

The resulting type after applying the / operator.
Source§

fn div(self, rhs: Ex) -> Matrix

Performs the / operation. Read more
Source§

impl Div<i64> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the / operator.
Source§

fn div(self, rhs: i64) -> Matrix

Performs the / operation. Read more
Source§

impl Div<i64> for Matrix

Source§

type Output = Matrix

The resulting type after applying the / operator.
Source§

fn div(self, rhs: i64) -> Matrix

Performs the / operation. Read more
Source§

impl Eq for Matrix

Source§

impl Index<(usize, usize)> for Matrix

Source§

fn index(&self, (i, j): (usize, usize)) -> &Ex

m[(i, j)] — panics on out-of-bounds like slice indexing.

Source§

type Output = Expr<Numeric>

The returned type after indexing.
Source§

impl IndexMut<(usize, usize)> for Matrix

Source§

fn index_mut(&mut self, (i, j): (usize, usize)) -> &mut Ex

Performs the mutable indexing (container[index]) operation. Read more
Source§

impl Mul for Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<&Expr<Numeric>> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: &Ex) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<&Expr<Numeric>> for Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: &Ex) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<&Matrix> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: &Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<&Matrix> for Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: &Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<&Matrix> for &Ex

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: &Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<&Matrix> for Ex

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: &Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<&Matrix> for i64

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: &Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<Expr<Numeric>> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: Ex) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<Expr<Numeric>> for Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: Ex) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<Matrix> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<Matrix> for &Ex

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<Matrix> for Ex

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<Matrix> for i64

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: Matrix) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<i64> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: i64) -> Matrix

Performs the * operation. Read more
Source§

impl Mul<i64> for Matrix

Source§

type Output = Matrix

The resulting type after applying the * operator.
Source§

fn mul(self, rhs: i64) -> Matrix

Performs the * operation. Read more
Source§

impl Neg for &Matrix

Source§

type Output = Matrix

The resulting type after applying the - operator.
Source§

fn neg(self) -> Matrix

Performs the unary - operation. Read more
Source§

impl Neg for Matrix

Source§

type Output = Matrix

The resulting type after applying the - operator.
Source§

fn neg(self) -> Matrix

Performs the unary - operation. Read more
Source§

impl PartialEq for Matrix

Source§

fn eq(&self, other: &Matrix) -> bool

Equality operator ==. Read more
1.0.0 (const: unstable) · Source§

fn ne(&self, other: &Rhs) -> bool

Inequality operator !=. Read more
Source§

impl StructuralPartialEq for Matrix

Source§

impl Sub for Matrix

Source§

type Output = Matrix

The resulting type after applying the - operator.
Source§

fn sub(self, rhs: Matrix) -> Matrix

Performs the - operation. Read more
Source§

impl Sub<&Matrix> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the - operator.
Source§

fn sub(self, rhs: &Matrix) -> Matrix

Performs the - operation. Read more
Source§

impl Sub<&Matrix> for Matrix

Source§

type Output = Matrix

The resulting type after applying the - operator.
Source§

fn sub(self, rhs: &Matrix) -> Matrix

Performs the - operation. Read more
Source§

impl Sub<Matrix> for &Matrix

Source§

type Output = Matrix

The resulting type after applying the - operator.
Source§

fn sub(self, rhs: Matrix) -> Matrix

Performs the - operation. Read more
Source§

impl TryFrom<&Matrix> for QMatrix

Source§

fn try_from(m: &Matrix) -> Result<Self, SymplexError>

Every entry must be a rational literal (after a constant-folding eval if the raw entries are not).

Source§

type Error = SymplexError

The type returned in the event of a conversion error.
Source§

impl TryFrom<&Matrix> for ZMatrix

Source§

fn try_from(m: &Matrix) -> Result<Self, SymplexError>

Every entry must be an integer literal (after a constant-folding eval if the raw entries are not).

Source§

type Error = SymplexError

The type returned in the event of a conversion error.
Source§

impl TryFrom<Vec<Vec<Expr<Numeric>>>> for Matrix

Source§

fn try_from(rows: Vec<Vec<Ex>>) -> Result<Self, Self::Error>

Same validation as Matrix::new.

Source§

type Error = SymplexError

The type returned in the event of a conversion error.

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T> ToString for T
where T: Display + ?Sized,

Source§

fn to_string(&self) -> String

Converts the given value to a String. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = !

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, !>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V

Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more