提交 f0bfae92 authored 作者: Tanjay94's avatar Tanjay94

Removed scipy version of MatrixPinv because numpy version was faster.

上级 97575d70
...@@ -17,6 +17,8 @@ from theano.gradient import DisconnectedType ...@@ -17,6 +17,8 @@ from theano.gradient import DisconnectedType
from theano.tensor.nlinalg import ( MatrixInverse, from theano.tensor.nlinalg import ( MatrixInverse,
matrix_inverse, matrix_inverse,
MatrixPinv,
pinv,
AllocDiag, AllocDiag,
alloc_diag, alloc_diag,
ExtractDiag, ExtractDiag,
...@@ -37,8 +39,6 @@ from theano.tensor.nlinalg import ( MatrixInverse, ...@@ -37,8 +39,6 @@ from theano.tensor.nlinalg import ( MatrixInverse,
from theano.tensor.slinalg import ( Cholesky, from theano.tensor.slinalg import ( Cholesky,
cholesky, cholesky,
CholeskyGrad, CholeskyGrad,
MatrixPinv,
pinv,
Solve, Solve,
solve, solve,
Eigvalsh, Eigvalsh,
......
...@@ -16,6 +16,56 @@ from theano.gof.opt import Optimizer ...@@ -16,6 +16,56 @@ from theano.gof.opt import Optimizer
from theano.gradient import DisconnectedType from theano.gradient import DisconnectedType
class MatrixPinv(Op):
"""Computes the pseudo-inverse of a matrix :math:`A`.
The pseudo-inverse of a matrix A, denoted :math:`A^+`, is
defined as: "the matrix that 'solves' [the least-squares problem]
:math:`Ax = b`," i.e., if :math:`\\bar{x}` is said solution, then
:math:`A^+` is that matrix such that :math:`\\bar{x} = A^+b`.
Note that :math:`Ax=AA^+b`, so :math:`AA^+` is close to the identity matrix.
This method is not faster then `matrix_inverse`. Its strength comes from
that it works for non-square matrices.
If you have a square matrix though, `matrix_inverse` can be both more
exact and faster to compute. Also this op does not get optimized into a
solve op.
"""
def __init__(self):
pass
def props(self):
"""Function exposing different properties of each instance of the
op.
For the ``MatrixPinv`` op, there are no properties to be exposed.
"""
return ()
def __hash__(self):
return hash((type(self), self.props()))
def __eq__(self, other):
return (type(self) == type(other) and self.props() == other.props())
def make_node(self, x):
x = as_tensor_variable(x)
assert x.ndim == 2
return Apply(self, [x], [x.type()])
def perform(self, node, (x,), (z, )):
try:
z[0] = numpy.linalg.pinv(x).astype(x.dtype)
except numpy.linalg.LinAlgError:
logger.debug('Failed to invert %s' % str(node.inputs[0]))
raise
def __str__(self):
return "MatrixPseudoInverse"
pinv = MatrixPinv()
class MatrixInverse(Op): class MatrixInverse(Op):
"""Computes the inverse of a matrix :math:`A`. """Computes the inverse of a matrix :math:`A`.
......
...@@ -173,59 +173,6 @@ class CholeskyGrad(Op): ...@@ -173,59 +173,6 @@ class CholeskyGrad(Op):
return [shapes[0]] return [shapes[0]]
class MatrixPinv(Op):
"""Computes the pseudo-inverse of a matrix :math:`A`.
The pseudo-inverse of a matrix A, denoted :math:`A^+`, is
defined as: "the matrix that 'solves' [the least-squares problem]
:math:`Ax = b`," i.e., if :math:`\\bar{x}` is said solution, then
:math:`A^+` is that matrix such that :math:`\\bar{x} = A^+b`.
Note that :math:`Ax=AA^+b`, so :math:`AA^+` is close to the identity matrix.
This method is not faster then `matrix_inverse`. Its strength comes from
that it works for non-square matrices.
If you have a square matrix though, `matrix_inverse` can be both more
exact and faster to compute. Also this op does not get optimized into a
solve op.
"""
def __init__(self):
pass
def props(self):
"""Function exposing different properties of each instance of the
op.
For the ``MatrixPinv`` op, there are no properties to be exposed.
"""
return ()
def __hash__(self):
return hash((type(self), self.props()))
def __eq__(self, other):
return (type(self) == type(other) and self.props() == other.props())
def make_node(self, x):
x = as_tensor_variable(x)
assert x.ndim == 2
return Apply(self, [x], [x.type()])
def perform(self, node, (x,), (z, )):
try:
if imported_scipy:
z[0] = scipy.linalg.pinv(x).astype(x.dtype)
else:
z[0] = numpy.linalg.pinv(x).astype(x.dtype)
except numpy.linalg.LinAlgError:
logger.debug('Failed to invert %s' % str(node.inputs[0]))
raise
def __str__(self):
return "MatrixPseudoInverse"
pinv = MatrixPinv()
class Solve(Op): class Solve(Op):
"""Solve a system of linear equations""" """Solve a system of linear equations"""
def __init__(self, def __init__(self,
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论