def european_call(self, r, sigma, T, Bu, m, n, Bl=0.0, barrier=None, method=None, isAmerican=False): """Compute prices for a European-style call option.""" X = linspace(0.0, B, n + 2) X = X[1:-1] Fp = clip(X - K, 0.0, 1e600) if barrier is None: Fu = B - K * exp(-r * linspace(0.0, T, m + 1)) Fl = zeros((m + 1, )) elif barrier == 'up-and-out': Fu = Fl = zeros((m + 1, )) bss = BSSolver(r, sigma, T, Bl, Bu, Fl, Fu, Fp, m, n, isAmerican) return X, bss.solve(method)
def european_call(r, sigma, T, Smax, m, n, Smin=0.0, barrier=None): X = linspace(0.0, Smax, n+2) X = X[1:-1] Fp = clip(X-K, 0.0, 1e600) if barrier is None: Fu = Smax - K*exp(-r * linspace(0.0, T, m+1)) Fl = zeros((m+1, )) elif barrier == 'up-and-out': Fu = Fl = zeros((m+1,)) bss = BS_FDM_cn(r, sigma, T, Smin, Smax, Fl, Fu, Fp, m, n) return X, bss.solve()
def det(a): """Compute the determinant of a matrix Parameters ---------- a : array-like, shape (M, M) Returns ------- det : float or complex Determinant of a Notes ----- The determinant is computed via LU factorization, LAPACK routine z/dgetrf. """ a = asarray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) n = a.shape[0] if isComplexType(t): lapack_routine = lapack_lite.zgetrf else: lapack_routine = lapack_lite.dgetrf pivots = zeros((n,), fortran_int) results = lapack_routine(n, n, a, n, pivots, 0) info = results['info'] if (info < 0): raise TypeError, "Illegal input to Fortran routine" elif (info > 0): return 0.0 sign = add.reduce(pivots != arange(1, n+1)) % 2 return (1.-2.*sign)*multiply.reduce(diagonal(a), axis=-1)
def european_put(r, sigma, T, Bu, m, n, Bl=0.0, barrier=None, method=None): """Compute prices for a European-style put option.""" X = linspace(0.0, B, n+2) X = X[1:-1] Fp = clip(K-X, 0.0, 1e600) if barrier is None: Fu = zeros((m+1,)) Fl = K*exp(-r * linspace(0.0, T, m+1)) elif barrier == 'up-and-out': Fu = Fl = zeros((m+1,)) bss = BlackScholesSolver(r, sigma, T, Bl, Bu, Fl, Fu, Fp, m, n) return X, bss.solve(method)
def _raw_fft(a, n=None, axis=-1, init_function=fftpack.cffti, work_function=fftpack.cfftf, fft_cache = _fft_cache ): a = asarray(a) if n == None: n = a.shape[axis] if n < 1: raise ValueError("Invalid number of FFT data points (%d) specified." % n) try: wsave = fft_cache[n] except(KeyError): wsave = init_function(n) fft_cache[n] = wsave if a.shape[axis] != n: s = list(a.shape) if s[axis] > n: index = [slice(None)]*len(s) index[axis] = slice(0,n) a = a[index] else: index = [slice(None)]*len(s) index[axis] = slice(0,s[axis]) s[axis] = n z = zeros(s, a.dtype.char) z[index] = a a = z if axis != -1: a = swapaxes(a, axis, -1) r = work_function(a, wsave) if axis != -1: r = swapaxes(r, axis, -1) return r
def solve(a, b): """Return the solution of a*x = b """ one_eq = len(b.shape) == 1 if one_eq: b = b[:, newaxis] _assertRank2(a, b) _assertSquareness(a) n_eq = a.shape[0] n_rhs = b.shape[1] if n_eq != b.shape[0]: raise LinAlgError, 'Incompatible dimensions' t, result_t = _commonType(a, b) # lapack_routine = _findLapackRoutine('gesv', t) if isComplexType(t): lapack_routine = lapack_lite.zgesv else: lapack_routine = lapack_lite.dgesv a, b = _fastCopyAndTranspose(t, a, b) pivots = zeros(n_eq, fortran_int) results = lapack_routine(n_eq, n_rhs, a, n_eq, pivots, b, n_eq, 0) if results['info'] > 0: raise LinAlgError, 'Singular matrix' if one_eq: return b.ravel().astype(result_t) else: return b.transpose().astype(result_t)
def test_vecself(self): """Ticket 844.""" # Inner product of a vector with itself segfaults or give meaningless # result a = zeros(shape=(1, 80), dtype=float64) p = inner_(a, a) assert_almost_equal(p, 0, decimal=DECPREC)
def _raw_fft(a, n, axis, is_real, is_forward, inv_norm): axis = normalize_axis_index(axis, a.ndim) if n is None: n = a.shape[axis] if n < 1: raise ValueError("Invalid number of FFT data points (%d) specified." % n) fct = 1 / inv_norm if a.shape[axis] != n: s = list(a.shape) index = [slice(None)] * len(s) if s[axis] > n: index[axis] = slice(0, n) a = a[tuple(index)] else: index[axis] = slice(0, s[axis]) s[axis] = n z = zeros(s, a.dtype.char) z[tuple(index)] = a a = z if axis == a.ndim - 1: r = pfi.execute(a, is_real, is_forward, fct) else: a = swapaxes(a, axis, -1) r = pfi.execute(a, is_real, is_forward, fct) r = swapaxes(r, axis, -1) return r
def test_vecself(self): """Ticket 844.""" # Inner product of a vector with itself segfaults or give meaningless # result a = zeros(shape = (1, 80), dtype = float64) p = inner_(a, a) assert_almost_equal(p, 0, decimal = DECPREC)
def det(a): """Compute the determinant of a matrix Parameters ---------- a : array-like, shape (M, M) Returns ------- det : float or complex Determinant of a Notes ----- The determinant is computed via LU factorization, LAPACK routine z/dgetrf. """ a = asarray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) n = a.shape[0] if isComplexType(t): lapack_routine = lapack_lite.zgetrf else: lapack_routine = lapack_lite.dgetrf pivots = zeros((n, ), fortran_int) results = lapack_routine(n, n, a, n, pivots, 0) info = results['info'] if (info < 0): raise TypeError, "Illegal input to Fortran routine" elif (info > 0): return 0.0 sign = add.reduce(pivots != arange(1, n + 1)) % 2 return (1. - 2. * sign) * multiply.reduce(diagonal(a), axis=-1)
def test_log2(self): a = nx.array([4.5, 2.3, 6.5]) out = nx.zeros(a.shape, float) tgt = nx.array([2.169925, 1.20163386, 2.70043972]) res = ufl.log2(a) assert_almost_equal(res, tgt) res = ufl.log2(a, out) assert_almost_equal(res, tgt) assert_almost_equal(out, tgt)
def prepare_kinetic_matrix(self, approach_matrix_size): # Dirty using side effect of fill_diagonal number_of_interval = self.approach_matrix_size - 1 step = abs(self.start_point - self.end_point) / number_of_interval self._kinetic_matrix = core.zeros( (approach_matrix_size, approach_matrix_size)) self.fill_diagonal(self._kinetic_matrix, -1, -0.5 / (step**2)) self.fill_diagonal(self._kinetic_matrix, 0, 1. / (step**2)) self.fill_diagonal(self._kinetic_matrix, 1, -0.5 / (step**2))
def test_isneginf(self): a = nx.array([nx.inf, -nx.inf, nx.nan, 0.0, 3.0, -3.0]) out = nx.zeros(a.shape, bool) tgt = nx.array([False, True, False, False, False, False]) res = ufl.isneginf(a) assert_equal(res, tgt) res = ufl.isneginf(a, out) assert_equal(res, tgt) assert_equal(out, tgt)
def __init__(self, ctx, positions, idents): self.idents = idents self.nident = int(max(idents))+1 self.flags = np.zeros(len(positions), dtype='u1') self.flags_updated = False assert len(idents) == len(positions) self.vb_positions = ctx.buffer(np.array(positions, dtype='f4', copy=False)) self.vb_idents = ctx.buffer(np.array(idents, dtype='u2', copy=False)) self.vb_flags = self.vb_flags = ctx.buffer(self.flags, dynamic=True) self.world = fmat4(1)
def test_fix(self): a = nx.array([[1.0, 1.1, 1.5, 1.8], [-1.0, -1.1, -1.5, -1.8]]) out = nx.zeros(a.shape, float) tgt = nx.array([[1., 1., 1., 1.], [-1., -1., -1., -1.]]) res = ufl.fix(a) assert_equal(res, tgt) res = ufl.fix(a, out) assert_equal(res, tgt) assert_equal(out, tgt) assert_equal(ufl.fix(3.14), 3)
def rand(*args): """Returns an array of random numbers with the given shape. This only uses the standard library, so it is useful for testing purposes. """ import random from numpy.core import zeros, float64 results = zeros(args, float64) f = results.flat for i in range(len(f)): f[i] = random.random() return results
def get_frequency_matrix(cluster_table: list, most_common: int): # List of most common words commons = list(most_common_counter(cluster_table, most_common).keys()) frequency_matrix = array(zeros((len(commons), len(cluster_table))), dtype=int) for j, counter in enumerate(cluster_table): for k in counter: if k in commons: i = commons.index(k) frequency_matrix[i][j] = counter[k] return commons, frequency_matrix
def _raw_fft( a, n=None, axis=-1, init_function=fftpack.cffti, work_function=fftpack.cfftf, fft_cache=_fft_cache, ): a = asarray(a) axis = normalize_axis_index(axis, a.ndim) if n is None: n = a.shape[axis] if n < 1: raise ValueError("Invalid number of FFT data points (%d) specified." % n) # We have to ensure that only a single thread can access a wsave array # at any given time. Thus we remove it from the cache and insert it # again after it has been used. Multiple threads might create multiple # copies of the wsave array. This is intentional and a limitation of # the current C code. wsave = fft_cache.pop_twiddle_factors(n) if wsave is None: wsave = init_function(n) if a.shape[axis] != n: s = list(a.shape) if s[axis] > n: index = [slice(None)] * len(s) index[axis] = slice(0, n) a = a[tuple(index)] else: index = [slice(None)] * len(s) index[axis] = slice(0, s[axis]) s[axis] = n z = zeros(s, a.dtype.char) z[tuple(index)] = a a = z if axis != a.ndim - 1: a = swapaxes(a, axis, -1) r = work_function(a, wsave) if axis != a.ndim - 1: r = swapaxes(r, axis, -1) # As soon as we put wsave back into the cache, another thread could pick it # up and start using it, so we must not do this until after we're # completely done using it ourselves. fft_cache.put_twiddle_factors(n, wsave) return r
def test_fill_primary_diagonal(self): size = 10 filled = 7 zero = core.zeros((size, size)) must_be = zero.copy() fill_diagonal(must_be, filled) current = Schrodinger_equation_solver.fill_diagonal( matrix=zero, diagonal_position=0, filled_value=filled) bul = current == must_be self.assertTrue(array_equal(must_be, current))
def test_isneginf(self): a = nx.array([nx.inf, -nx.inf, nx.nan, 0.0, 3.0, -3.0]) out = nx.zeros(a.shape, bool) tgt = nx.array([False, True, False, False, False, False]) res = ufl.isneginf(a) assert_equal(res, tgt) res = ufl.isneginf(a, out) assert_equal(res, tgt) assert_equal(out, tgt) a = a.astype(np.complex_) with assert_raises(TypeError): ufl.isneginf(a)
def test_isneginf(self): a = nx.array([nx.inf, -nx.inf, nx.nan, 0.0, 3.0, -3.0]) out = nx.zeros(a.shape, bool) tgt = nx.array([False, True, False, False, False, False]) res = ufl.isneginf(a) assert_equal(res, tgt) res = ufl.isneginf(a, out) assert_equal(res, tgt) assert_equal(out, tgt) a = a.astype(np.complex) with assert_raises(TypeError): ufl.isneginf(a)
def test_fill_side_diagonal(self): filled = 1. down_diagonal = [[0., 0.], [filled, 0.]] up_diagonal = [[0., filled], [0., 0.]] staple = core.zeros((2, 2)) counted_down_diagonal = Schrodinger_equation_solver.fill_diagonal( matrix=staple.copy(), diagonal_position=-1, filled_value=filled) counted_up_diagonal = Schrodinger_equation_solver.fill_diagonal( matrix=staple.copy(), diagonal_position=1, filled_value=filled) self.assertTrue(array_equal(down_diagonal, counted_down_diagonal)) self.assertTrue(array_equal(up_diagonal, counted_up_diagonal))
def _raw_fft(a, n=None, axis=-1, init_function=fftpack.cffti, work_function=fftpack.cfftf, fft_cache=_fft_cache): a = asarray(a) if n is None: n = a.shape[axis] if n < 1: raise ValueError("Invalid number of FFT data points (%d) specified." % n) try: # Thread-safety note: We rely on list.pop() here to atomically # retrieve-and-remove a wsave from the cache. This ensures that no # other thread can get the same wsave while we're using it. wsave = fft_cache.setdefault(n, []).pop() except (IndexError): wsave = init_function(n) if a.shape[axis] != n: s = list(a.shape) if s[axis] > n: index = [slice(None)] * len(s) index[axis] = slice(0, n) a = a[index] else: index = [slice(None)] * len(s) index[axis] = slice(0, s[axis]) s[axis] = n z = zeros(s, a.dtype.char) z[index] = a a = z if axis != -1: a = swapaxes(a, axis, -1) r = work_function(a, wsave) if axis != -1: r = swapaxes(r, axis, -1) # As soon as we put wsave back into the cache, another thread could pick it # up and start using it, so we must not do this until after we're # completely done using it ourselves. fft_cache[n].append(wsave) return r
def _raw_fft(a, n=None, axis=-1, init_function=fftpack.cffti, work_function=fftpack.cfftf, fft_cache=_fft_cache): a = asarray(a) axis = normalize_axis_index(axis, a.ndim) if n is None: n = a.shape[axis] if n < 1: raise ValueError("Invalid number of FFT data points (%d) specified." % n) # We have to ensure that only a single thread can access a wsave array # at any given time. Thus we remove it from the cache and insert it # again after it has been used. Multiple threads might create multiple # copies of the wsave array. This is intentional and a limitation of # the current C code. wsave = fft_cache.pop_twiddle_factors(n) if wsave is None: wsave = init_function(n) if a.shape[axis] != n: s = list(a.shape) if s[axis] > n: index = [slice(None)]*len(s) index[axis] = slice(0, n) a = a[tuple(index)] else: index = [slice(None)]*len(s) index[axis] = slice(0, s[axis]) s[axis] = n z = zeros(s, a.dtype.char) z[tuple(index)] = a a = z if axis != a.ndim - 1: a = swapaxes(a, axis, -1) r = work_function(a, wsave) if axis != a.ndim - 1: r = swapaxes(r, axis, -1) # As soon as we put wsave back into the cache, another thread could pick it # up and start using it, so we must not do this until after we're # completely done using it ourselves. fft_cache.put_twiddle_factors(n, wsave) return r
def det(a): """ Compute the determinant of an array. Parameters ---------- a : array_like, shape (M, M) Input array. Returns ------- det : ndarray Determinant of `a`. Notes ----- The determinant is computed via LU factorization using the LAPACK routine z/dgetrf. Examples -------- The determinant of a 2-D array [[a, b], [c, d]] is ad - bc: >>> a = np.array([[1, 2], [3, 4]]) >>> np.linalg.det(a) -2.0 """ a = asarray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) n = a.shape[0] if isComplexType(t): lapack_routine = lapack_lite.zgetrf else: lapack_routine = lapack_lite.dgetrf pivots = zeros((n,), fortran_int) results = lapack_routine(n, n, a, n, pivots, 0) info = results['info'] if (info < 0): raise TypeError, "Illegal input to Fortran routine" elif (info > 0): return 0.0 sign = add.reduce(pivots != arange(1, n+1)) % 2 return (1.-2.*sign)*multiply.reduce(diagonal(a), axis=-1)
def det(a): """ Compute the determinant of an array. Parameters ---------- a : array_like, shape (M, M) Input array. Returns ------- det : ndarray Determinant of `a`. Notes ----- The determinant is computed via LU factorization using the LAPACK routine z/dgetrf. Examples -------- The determinant of a 2-D array [[a, b], [c, d]] is ad - bc: >>> a = np.array([[1, 2], [3, 4]]) >>> np.linalg.det(a) -2.0 """ a = asarray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) n = a.shape[0] if isComplexType(t): lapack_routine = lapack_lite.zgetrf else: lapack_routine = lapack_lite.dgetrf pivots = zeros((n, ), fortran_int) results = lapack_routine(n, n, a, n, pivots, 0) info = results['info'] if (info < 0): raise TypeError, "Illegal input to Fortran routine" elif (info > 0): return 0.0 sign = add.reduce(pivots != arange(1, n + 1)) % 2 return (1. - 2. * sign) * multiply.reduce(diagonal(a), axis=-1)
def _raw_fft(a, n=None, axis=-1, init_function=fftpack.cffti, work_function=fftpack.cfftf, fft_cache=_fft_cache): a = asarray(a) if n is None: n = a.shape[axis] if n < 1: raise ValueError("Invalid number of FFT data points (%d) specified." % n) try: # Thread-safety note: We rely on list.pop() here to atomically # retrieve-and-remove a wsave from the cache. This ensures that no # other thread can get the same wsave while we're using it. wsave = fft_cache.setdefault(n, []).pop() except (IndexError): wsave = init_function(n) if a.shape[axis] != n: s = list(a.shape) if s[axis] > n: index = [slice(None)]*len(s) index[axis] = slice(0, n) a = a[index] else: index = [slice(None)]*len(s) index[axis] = slice(0, s[axis]) s[axis] = n z = zeros(s, a.dtype.char) z[index] = a a = z if axis != -1: a = swapaxes(a, axis, -1) r = work_function(a, wsave) if axis != -1: r = swapaxes(r, axis, -1) # As soon as we put wsave back into the cache, another thread could pick it # up and start using it, so we must not do this until after we're # completely done using it ourselves. fft_cache[n].append(wsave) return r
def solve(a, b): """Solve the equation a x = b Parameters ---------- a : array-like, shape (M, M) b : array-like, shape (M,) Returns ------- x : array, shape (M,) Raises LinAlgError if a is singular or not square """ a, _ = _makearray(a) b, wrap = _makearray(b) one_eq = len(b.shape) == 1 if one_eq: b = b[:, newaxis] _assertRank2(a, b) _assertSquareness(a) n_eq = a.shape[0] n_rhs = b.shape[1] if n_eq != b.shape[0]: raise LinAlgError, 'Incompatible dimensions' t, result_t = _commonType(a, b) # lapack_routine = _findLapackRoutine('gesv', t) if isComplexType(t): lapack_routine = lapack_lite.zgesv else: lapack_routine = lapack_lite.dgesv a, b = _fastCopyAndTranspose(t, a, b) pivots = zeros(n_eq, fortran_int) results = lapack_routine(n_eq, n_rhs, a, n_eq, pivots, b, n_eq, 0) if results['info'] > 0: raise LinAlgError, 'Singular matrix' if one_eq: return wrap(b.ravel().astype(result_t)) else: return wrap(b.transpose().astype(result_t))
def _raw_fft(a, n=None, axis=-1, init_function=fftpack.cffti, work_function=fftpack.cfftf, fft_cache=_fft_cache): a = asarray(a) if n is None: n = a.shape[axis] if n < 1: raise ValueError("Invalid number of FFT data points (%d) specified." % n) try: wsave = fft_cache[n] except (KeyError): wsave = init_function(n) fft_cache[n] = wsave if a.shape[axis] != n: s = list(a.shape) if s[axis] > n: index = [slice(None)] * len(s) index[axis] = slice(0, n) a = a[index] else: index = [slice(None)] * len(s) index[axis] = slice(0, s[axis]) s[axis] = n z = zeros(s, a.dtype.char) z[index] = a a = z if axis != -1: a = swapaxes(a, axis, -1) r = work_function(a, wsave) if axis != -1: r = swapaxes(r, axis, -1) return r
def ifftpad(a, n, scale=True): """ Pad the spectrum at high frequencies. The padding done by the `ifft` function appends zeros to the end of the spectrum which shifts the frequencies and can make the resulting signal differ from the non-padded version. This function pads the spectrum by putting the zeros in the middle where the highest frequencies are. Taking the `ifft` of this padded version result in a signal that is an interpolated version of the unpadded signal, which is what is expected. Parameters ---------- a : array_like Input array, can be complex. n : int Length of the padded spectrum. `n` should be larger than the length of the input. scale : bool, optional Whether to scale the spectrum or not. The `ifft` function divides by the input length which will be the incorrect length for a padded spectrum. Setting this parameter will pre-scale the spectrum so that dividing by the padded length will be correct. Returns ------- out : ndarray The spectrum padded to length `n`. Possibly scaled as well. Examples -------- >>> spectrum = np.array([0, 1, 2, -3, -2, -1]) >>> np.fft.ifftpad(spectrum, 10, scale=False) array([ 0., 1., 2., 0., 0., 0., 0., -3., -2., -1.]) """ spectrum = concatenate((a[:len(a) // 2], zeros(n - len(a)), a[len(a) // 2:])) if scale: spectrum *= (n / len(a)) return spectrum
def det(a): "The determinant of the 2-d array a" a = asarray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) n = a.shape[0] if isComplexType(t): lapack_routine = lapack_lite.zgetrf else: lapack_routine = lapack_lite.dgetrf pivots = zeros((n, ), fortran_int) results = lapack_routine(n, n, a, n, pivots, 0) info = results['info'] if (info < 0): raise TypeError, "Illegal input to Fortran routine" elif (info > 0): return 0.0 sign = add.reduce(pivots != arange(1, n + 1)) % 2 return (1. - 2. * sign) * multiply.reduce(diagonal(a), axis=-1)
def det(a): "The determinant of the 2-d array a" a = asarray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) n = a.shape[0] if isComplexType(t): lapack_routine = lapack_lite.zgetrf else: lapack_routine = lapack_lite.dgetrf pivots = zeros((n,), fortran_int) results = lapack_routine(n, n, a, n, pivots, 0) info = results['info'] if (info < 0): raise TypeError, "Illegal input to Fortran routine" elif (info > 0): return 0.0 sign = add.reduce(pivots != arange(1, n+1)) % 2 return (1.-2.*sign)*multiply.reduce(diagonal(a), axis=-1)
def eigh(a, UPLO='L'): """ Eigenvalues and eigenvectors of a Hermitian or real symmetric matrix. Parameters ---------- a : array_like, shape (M, M) A complex Hermitian or symmetric real matrix. UPLO : {'L', 'U'}, optional Specifies whether the calculation is done with data from the lower triangular part of `a` ('L', default) or the upper triangular part ('U'). Returns ------- w : ndarray, shape (M,) The eigenvalues. The eigenvalues are not necessarily ordered. v : ndarray, shape (M, M) The normalized eigenvector corresponding to the eigenvalue w[i] is the column v[:,i]. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eigvalsh : eigenvalues of symmetric or Hemitiean arrays. eig : eigenvalues and right eigenvectors for non-symmetric arrays eigvals : eigenvalues of non-symmetric array. Notes ----- A simple interface to the LAPACK routines dsyevd and zheevd that compute the eigenvalues and eigenvectors of real symmetric and complex Hermitian arrays respectively. The number w is an eigenvalue of a if there exists a vector v satisfying the equation dot(a,v) = w*v. Alternately, if w is a root of the characteristic equation det(a - w[i]*I) = 0, where det is the determinant and I is the identity matrix. The eigenvalues of real symmetric or complex Hermitean matrices are always real. The array v of eigenvectors is unitary and a, w, and v satisfy the equation dot(a,v[i]) = w[i]*v[:,i]. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) n = a.shape[0] liwork = 5*n+3 iwork = zeros((liwork,), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zheevd w = zeros((n,), real_t) lwork = 1 work = zeros((lwork,), t) lrwork = 1 rwork = zeros((lrwork,), real_t) results = lapack_routine('V', UPLO, n, a, n, w, work, -1, rwork, -1, iwork, liwork, 0) lwork = int(abs(work[0])) work = zeros((lwork,), t) lrwork = int(rwork[0]) rwork = zeros((lrwork,), real_t) results = lapack_routine('V', UPLO, n, a, n, w, work, lwork, rwork, lrwork, iwork, liwork, 0) else: lapack_routine = lapack_lite.dsyevd w = zeros((n,), t) lwork = 1 work = zeros((lwork,), t) results = lapack_routine('V', UPLO, n, a, n, w, work, -1, iwork, liwork, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine('V', UPLO, n, a, n, w, work, lwork, iwork, liwork, 0) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' at = a.transpose().astype(result_t) return w.astype(_realType(result_t)), wrap(at)
def eig(a): """ Compute eigenvalues and right eigenvectors of an array. Parameters ---------- a : array_like, shape (M, M) A complex or real 2-D array. Returns ------- w : ndarray, shape (M,) The eigenvalues, each repeated according to its multiplicity. The eigenvalues are not necessarily ordered, nor are they necessarily real for real matrices. v : ndarray, shape (M, M) The normalized eigenvector corresponding to the eigenvalue ``w[i]`` is the column ``v[:,i]``. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eigvalsh : eigenvalues of symmetric or Hemitiean arrays. eig : eigenvalues and right eigenvectors for non-symmetric arrays eigvals : eigenvalues of non-symmetric array. Notes ----- This is a simple interface to the LAPACK routines dgeev and zgeev that compute the eigenvalues and eigenvectors of general real and complex arrays respectively. The number `w` is an eigenvalue of a if there exists a vector `v` satisfying the equation ``dot(a,v) = w*v``. Alternately, if `w` is a root of the characteristic equation ``det(a - w[i]*I) = 0``, where `det` is the determinant and `I` is the identity matrix. The arrays `a`, `w`, and `v` satisfy the equation ``dot(a,v[i]) = w[i]*v[:,i]``. The array `v` of eigenvectors may not be of maximum rank, that is, some of the columns may be dependent, although roundoff error may obscure that fact. If the eigenvalues are all different, then theoretically the eigenvectors are independent. Likewise, the matrix of eigenvectors is unitary if the matrix `a` is normal, i.e., if ``dot(a, a.H) = dot(a.H, a)``. The left and right eigenvectors are not necessarily the (Hermitian) transposes of each other. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) _assertFinite(a) a, t, result_t = _convertarray(a) # convert to double or cdouble type real_t = _linalgRealType(t) n = a.shape[0] dummy = zeros((1,), t) if isComplexType(t): # Complex routines take different arguments lapack_routine = lapack_lite.zgeev w = zeros((n,), t) v = zeros((n, n), t) lwork = 1 work = zeros((lwork,), t) rwork = zeros((2*n,), real_t) results = lapack_routine('N', 'V', n, a, n, w, dummy, 1, v, n, work, -1, rwork, 0) lwork = int(abs(work[0])) work = zeros((lwork,), t) results = lapack_routine('N', 'V', n, a, n, w, dummy, 1, v, n, work, lwork, rwork, 0) else: lapack_routine = lapack_lite.dgeev wr = zeros((n,), t) wi = zeros((n,), t) vr = zeros((n, n), t) lwork = 1 work = zeros((lwork,), t) results = lapack_routine('N', 'V', n, a, n, wr, wi, dummy, 1, vr, n, work, -1, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine('N', 'V', n, a, n, wr, wi, dummy, 1, vr, n, work, lwork, 0) if all(wi == 0.0): w = wr v = vr result_t = _realType(result_t) else: w = wr+1j*wi v = array(vr, w.dtype) ind = flatnonzero(wi != 0.0) # indices of complex e-vals for i in range(len(ind)/2): v[ind[2*i]] = vr[ind[2*i]] + 1j*vr[ind[2*i+1]] v[ind[2*i+1]] = vr[ind[2*i]] - 1j*vr[ind[2*i+1]] result_t = _complexType(result_t) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' vt = v.transpose().astype(result_t) return w.astype(result_t), wrap(vt)
def eigvalsh(a, UPLO='L'): """ Compute the eigenvalues of a Hermitean or real symmetric matrix. Parameters ---------- a : array_like, shape (M, M) A complex or real matrix whose eigenvalues and eigenvectors will be computed. UPLO : {'L', 'U'}, optional Specifies whether the calculation is done with data from the lower triangular part of `a` ('L', default) or the upper triangular part ('U'). Returns ------- w : ndarray, shape (M,) The eigenvalues, each repeated according to its multiplicity. They are not necessarily ordered. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eigh : eigenvalues and eigenvectors of symmetric/Hermitean arrays. eigvals : eigenvalues of general real or complex arrays. eig : eigenvalues and eigenvectors of general real or complex arrays. Notes ----- This is a simple interface to the LAPACK routines dsyevd and zheevd that sets the flags to return only the eigenvalues of real symmetric and complex Hermetian arrays respectively. The number w is an eigenvalue of a if there exists a vector v satisfying the equation dot(a,v) = w*v. Alternately, if w is a root of the characteristic equation det(a - w[i]*I) = 0, where det is the determinant and I is the identity matrix. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) n = a.shape[0] liwork = 5*n+3 iwork = zeros((liwork,), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zheevd w = zeros((n,), real_t) lwork = 1 work = zeros((lwork,), t) lrwork = 1 rwork = zeros((lrwork,), real_t) results = lapack_routine('N', UPLO, n, a, n, w, work, -1, rwork, -1, iwork, liwork, 0) lwork = int(abs(work[0])) work = zeros((lwork,), t) lrwork = int(rwork[0]) rwork = zeros((lrwork,), real_t) results = lapack_routine('N', UPLO, n, a, n, w, work, lwork, rwork, lrwork, iwork, liwork, 0) else: lapack_routine = lapack_lite.dsyevd w = zeros((n,), t) lwork = 1 work = zeros((lwork,), t) results = lapack_routine('N', UPLO, n, a, n, w, work, -1, iwork, liwork, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine('N', UPLO, n, a, n, w, work, lwork, iwork, liwork, 0) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' return w.astype(result_t)
def eigvals(a): """ Compute the eigenvalues of a general matrix. Parameters ---------- a : array_like, shape (M, M) A complex or real matrix whose eigenvalues and eigenvectors will be computed. Returns ------- w : ndarray, shape (M,) The eigenvalues, each repeated according to its multiplicity. They are not necessarily ordered, nor are they necessarily real for real matrices. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eig : eigenvalues and right eigenvectors of general arrays eigvalsh : eigenvalues of symmetric or Hemitiean arrays. eigh : eigenvalues and eigenvectors of symmetric/Hermitean arrays. Notes ----- This is a simple interface to the LAPACK routines dgeev and zgeev that sets the flags to return only the eigenvalues of general real and complex arrays respectively. The number w is an eigenvalue of a if there exists a vector v satisfying the equation dot(a,v) = w*v. Alternately, if w is a root of the characteristic equation det(a - w[i]*I) = 0, where det is the determinant and I is the identity matrix. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) _assertFinite(a) t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) n = a.shape[0] dummy = zeros((1,), t) if isComplexType(t): lapack_routine = lapack_lite.zgeev w = zeros((n,), t) rwork = zeros((n,), real_t) lwork = 1 work = zeros((lwork,), t) results = lapack_routine('N', 'N', n, a, n, w, dummy, 1, dummy, 1, work, -1, rwork, 0) lwork = int(abs(work[0])) work = zeros((lwork,), t) results = lapack_routine('N', 'N', n, a, n, w, dummy, 1, dummy, 1, work, lwork, rwork, 0) else: lapack_routine = lapack_lite.dgeev wr = zeros((n,), t) wi = zeros((n,), t) lwork = 1 work = zeros((lwork,), t) results = lapack_routine('N', 'N', n, a, n, wr, wi, dummy, 1, dummy, 1, work, -1, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine('N', 'N', n, a, n, wr, wi, dummy, 1, dummy, 1, work, lwork, 0) if all(wi == 0.): w = wr result_t = _realType(result_t) else: w = wr+1j*wi result_t = _complexType(result_t) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' return w.astype(result_t)
def eigh(a, UPLO='L'): """ Eigenvalues and eigenvectors of a Hermitian or real symmetric matrix. Parameters ---------- a : array_like, shape (M, M) A complex Hermitian or symmetric real matrix. UPLO : {'L', 'U'}, optional Specifies whether the calculation is done with data from the lower triangular part of `a` ('L', default) or the upper triangular part ('U'). Returns ------- w : ndarray, shape (M,) The eigenvalues. The eigenvalues are not necessarily ordered. v : ndarray, shape (M, M) The normalized eigenvector corresponding to the eigenvalue w[i] is the column v[:,i]. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eigvalsh : eigenvalues of symmetric or Hemitiean arrays. eig : eigenvalues and right eigenvectors for non-symmetric arrays eigvals : eigenvalues of non-symmetric array. Notes ----- A simple interface to the LAPACK routines dsyevd and zheevd that compute the eigenvalues and eigenvectors of real symmetric and complex Hermitian arrays respectively. The number w is an eigenvalue of a if there exists a vector v satisfying the equation dot(a,v) = w*v. Alternately, if w is a root of the characteristic equation det(a - w[i]*I) = 0, where det is the determinant and I is the identity matrix. The eigenvalues of real symmetric or complex Hermitean matrices are always real. The array v of eigenvectors is unitary and a, w, and v satisfy the equation dot(a,v[i]) = w[i]*v[:,i]. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) n = a.shape[0] liwork = 5 * n + 3 iwork = zeros((liwork, ), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zheevd w = zeros((n, ), real_t) lwork = 1 work = zeros((lwork, ), t) lrwork = 1 rwork = zeros((lrwork, ), real_t) results = lapack_routine('V', UPLO, n, a, n, w, work, -1, rwork, -1, iwork, liwork, 0) lwork = int(abs(work[0])) work = zeros((lwork, ), t) lrwork = int(rwork[0]) rwork = zeros((lrwork, ), real_t) results = lapack_routine('V', UPLO, n, a, n, w, work, lwork, rwork, lrwork, iwork, liwork, 0) else: lapack_routine = lapack_lite.dsyevd w = zeros((n, ), t) lwork = 1 work = zeros((lwork, ), t) results = lapack_routine('V', UPLO, n, a, n, w, work, -1, iwork, liwork, 0) lwork = int(work[0]) work = zeros((lwork, ), t) results = lapack_routine('V', UPLO, n, a, n, w, work, lwork, iwork, liwork, 0) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' at = a.transpose().astype(result_t) return w.astype(_realType(result_t)), wrap(at)
def coarseMolSurface(molFrag,XYZd,isovalue=5.0,resolution=-0.4,padding=0.0, name='CoarseMolSurface',geom=None): """ Function adapted from the Vision network which compute a coarse molecular surface in PMV @type molFrag: MolKit.AtomSet @param molFrag: the atoms selection @type XYZd: array @param XYZd: shape of the volume @type isovalue: float @param isovalue: isovalue for the isosurface computation @type resolution: float @param resolution: resolution of the final mesh @type padding: float @param padding: the padding @type name: string @param name: the name of the resultante geometry @type geom: DejaVu.Geom @param geom: update geom instead of creating a new one @rtype: DejaVu.Geom @return: the created or updated DejaVu.Geom """ import pdb from MolKit.molecule import Atom atoms = molFrag.findType(Atom) coords = atoms.coords radii = atoms.vdwRadius from UTpackages.UTblur import blur import numpy.core as Numeric volarr, origin, span = blur.generateBlurmap(coords, radii, XYZd,resolution, padding = 0.0) volarr.shape = (XYZd[0],XYZd[1],XYZd[2]) volarr = Numeric.ascontiguousarray(Numeric.transpose(volarr), 'f') weights = Numeric.ones(len(radii), 'f') h = {} from Volume.Grid3D import Grid3DF maskGrid = Grid3DF( volarr, origin, span , h) h['amin'], h['amax'],h['amean'],h['arms']= maskGrid.stats() from UTpackages.UTisocontour import isocontour isocontour.setVerboseLevel(0) data = maskGrid.data origin = Numeric.array(maskGrid.origin).astype('f') stepsize = Numeric.array(maskGrid.stepSize).astype('f') if data.dtype.char!=Numeric.float32: data = data.astype('f')#Numeric.Float32) newgrid3D = Numeric.ascontiguousarray(Numeric.reshape( Numeric.transpose(data), (1, 1)+tuple(data.shape) ), data.dtype.char) ndata = isocontour.newDatasetRegFloat3D(newgrid3D, origin, stepsize) isoc = isocontour.getContour3d(ndata, 0, 0, isovalue, isocontour.NO_COLOR_VARIABLE) vert = Numeric.zeros((isoc.nvert,3)).astype('f') norm = Numeric.zeros((isoc.nvert,3)).astype('f') col = Numeric.zeros((isoc.nvert)).astype('f') tri = Numeric.zeros((isoc.ntri,3)).astype('i') isocontour.getContour3dData(isoc, vert, norm, col, tri, 0) if maskGrid.crystal: vert = maskGrid.crystal.toCartesian(vert) return (vert, tri)
def eigvalsh(a, UPLO='L'): """ Compute the eigenvalues of a Hermitean or real symmetric matrix. Parameters ---------- a : array_like, shape (M, M) A complex or real matrix whose eigenvalues and eigenvectors will be computed. UPLO : {'L', 'U'}, optional Specifies whether the calculation is done with data from the lower triangular part of `a` ('L', default) or the upper triangular part ('U'). Returns ------- w : ndarray, shape (M,) The eigenvalues, each repeated according to its multiplicity. They are not necessarily ordered. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eigh : eigenvalues and eigenvectors of symmetric/Hermitean arrays. eigvals : eigenvalues of general real or complex arrays. eig : eigenvalues and eigenvectors of general real or complex arrays. Notes ----- This is a simple interface to the LAPACK routines dsyevd and zheevd that sets the flags to return only the eigenvalues of real symmetric and complex Hermetian arrays respectively. The number w is an eigenvalue of a if there exists a vector v satisfying the equation dot(a,v) = w*v. Alternately, if w is a root of the characteristic equation det(a - w[i]*I) = 0, where det is the determinant and I is the identity matrix. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) n = a.shape[0] liwork = 5 * n + 3 iwork = zeros((liwork, ), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zheevd w = zeros((n, ), real_t) lwork = 1 work = zeros((lwork, ), t) lrwork = 1 rwork = zeros((lrwork, ), real_t) results = lapack_routine('N', UPLO, n, a, n, w, work, -1, rwork, -1, iwork, liwork, 0) lwork = int(abs(work[0])) work = zeros((lwork, ), t) lrwork = int(rwork[0]) rwork = zeros((lrwork, ), real_t) results = lapack_routine('N', UPLO, n, a, n, w, work, lwork, rwork, lrwork, iwork, liwork, 0) else: lapack_routine = lapack_lite.dsyevd w = zeros((n, ), t) lwork = 1 work = zeros((lwork, ), t) results = lapack_routine('N', UPLO, n, a, n, w, work, -1, iwork, liwork, 0) lwork = int(work[0]) work = zeros((lwork, ), t) results = lapack_routine('N', UPLO, n, a, n, w, work, lwork, iwork, liwork, 0) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' return w.astype(result_t)
def solve(a, b): """ Solve the equation ``a x = b`` for ``x``. Parameters ---------- a : array_like, shape (M, M) Input equation coefficients. b : array_like, shape (M,) Equation target values. Returns ------- x : array, shape (M,) Raises ------ LinAlgError If `a` is singular or not square. Notes ----- ``linalg.solve`` is a wrapper to the LAPACK http://www.netlib.org/lapack routines `dgesv`_ and `zgesv`_. The solution to the system of linear equations is computed using an LU decomposition with partial pivoting and row interchanges. .. _dgesv: http://www.netlib.org/lapack/double/dgesv.f .. _zgesv: http://www.netlib.org/lapack/complex16/zgesv.f Examples -------- Solve the system of equations ``3 * x0 + x1 = 9`` and ``x0 + 2 * x1 = 8``: >>> a = np.array([[3,1], [1,2]]) >>> b = np.array([9,8]) >>> x = np.linalg.solve(a, b) >>> x array([ 2., 3.]) Check that the solution is correct: >>> (np.dot(a, x) == b).all() True """ a, _ = _makearray(a) b, wrap = _makearray(b) one_eq = len(b.shape) == 1 if one_eq: b = b[:, newaxis] _assertRank2(a, b) _assertSquareness(a) n_eq = a.shape[0] n_rhs = b.shape[1] if n_eq != b.shape[0]: raise LinAlgError, 'Incompatible dimensions' t, result_t = _commonType(a, b) # lapack_routine = _findLapackRoutine('gesv', t) if isComplexType(t): lapack_routine = lapack_lite.zgesv else: lapack_routine = lapack_lite.dgesv a, b = _fastCopyAndTranspose(t, a, b) pivots = zeros(n_eq, fortran_int) results = lapack_routine(n_eq, n_rhs, a, n_eq, pivots, b, n_eq, 0) if results['info'] > 0: raise LinAlgError, 'Singular matrix' if one_eq: return wrap(b.ravel().astype(result_t)) else: return wrap(b.transpose().astype(result_t))
def eig(a): """ Compute eigenvalues and right eigenvectors of an array. Parameters ---------- a : array_like, shape (M, M) A complex or real 2-D array. Returns ------- w : ndarray, shape (M,) The eigenvalues, each repeated according to its multiplicity. The eigenvalues are not necessarily ordered, nor are they necessarily real for real matrices. v : ndarray, shape (M, M) The normalized eigenvector corresponding to the eigenvalue ``w[i]`` is the column ``v[:,i]``. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eigvalsh : eigenvalues of symmetric or Hemitiean arrays. eig : eigenvalues and right eigenvectors for non-symmetric arrays eigvals : eigenvalues of non-symmetric array. Notes ----- This is a simple interface to the LAPACK routines dgeev and zgeev that compute the eigenvalues and eigenvectors of general real and complex arrays respectively. The number `w` is an eigenvalue of a if there exists a vector `v` satisfying the equation ``dot(a,v) = w*v``. Alternately, if `w` is a root of the characteristic equation ``det(a - w[i]*I) = 0``, where `det` is the determinant and `I` is the identity matrix. The arrays `a`, `w`, and `v` satisfy the equation ``dot(a,v[i]) = w[i]*v[:,i]``. The array `v` of eigenvectors may not be of maximum rank, that is, some of the columns may be dependent, although roundoff error may obscure that fact. If the eigenvalues are all different, then theoretically the eigenvectors are independent. Likewise, the matrix of eigenvectors is unitary if the matrix `a` is normal, i.e., if ``dot(a, a.H) = dot(a.H, a)``. The left and right eigenvectors are not necessarily the (Hermitian) transposes of each other. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) _assertFinite(a) a, t, result_t = _convertarray(a) # convert to double or cdouble type real_t = _linalgRealType(t) n = a.shape[0] dummy = zeros((1, ), t) if isComplexType(t): # Complex routines take different arguments lapack_routine = lapack_lite.zgeev w = zeros((n, ), t) v = zeros((n, n), t) lwork = 1 work = zeros((lwork, ), t) rwork = zeros((2 * n, ), real_t) results = lapack_routine('N', 'V', n, a, n, w, dummy, 1, v, n, work, -1, rwork, 0) lwork = int(abs(work[0])) work = zeros((lwork, ), t) results = lapack_routine('N', 'V', n, a, n, w, dummy, 1, v, n, work, lwork, rwork, 0) else: lapack_routine = lapack_lite.dgeev wr = zeros((n, ), t) wi = zeros((n, ), t) vr = zeros((n, n), t) lwork = 1 work = zeros((lwork, ), t) results = lapack_routine('N', 'V', n, a, n, wr, wi, dummy, 1, vr, n, work, -1, 0) lwork = int(work[0]) work = zeros((lwork, ), t) results = lapack_routine('N', 'V', n, a, n, wr, wi, dummy, 1, vr, n, work, lwork, 0) if all(wi == 0.0): w = wr v = vr result_t = _realType(result_t) else: w = wr + 1j * wi v = array(vr, w.dtype) ind = flatnonzero(wi != 0.0) # indices of complex e-vals for i in range(len(ind) / 2): v[ind[2 * i]] = vr[ind[2 * i]] + 1j * vr[ind[2 * i + 1]] v[ind[2 * i + 1]] = vr[ind[2 * i]] - 1j * vr[ind[2 * i + 1]] result_t = _complexType(result_t) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' vt = v.transpose().astype(result_t) return w.astype(result_t), wrap(vt)
# Get transformation coefficients, and print them out figure = figures[opts.figure] a, b = schwarz_christoffel_coeff(figure) print a print b+1.0 # Set up discretization points for the grid M = opts.M N = opts.N * len(figure) R = 1.0 - 2**linspace(0, -M, M+1, endpoint=True) Theta = linspace(0, 2*pi, N, endpoint=False) if not opts.show_domain: # Compute f(z) over grid W = zeros(shape=(M, N), dtype=complex) for v in xrange(0, N): Z = R * exp(1j*Theta[v]) for u in xrange(0, M): W[u,v] = gauss_quad32(schwarz_christoffel_integrand, (a, b, Z[u], Z[u+1]-Z[u])) W = cumsum(W, axis=0) else: # Domain contours are just concentric circles W = 36.0 * R[1:].reshape(-1,1) * exp(1j*Theta).reshape(1,-1) # Start vector drawing with PyX unit.set(uscale=0.075) cvs = canvas.canvas() if opts.show_wavefronts:
def svd(a, full_matrices=1, compute_uv=1): """ Singular Value Decomposition. Factorizes the matrix `a` into two unitary matrices, ``U`` and ``Vh``, and a 1-dimensional array of singular values, ``s`` (real, non-negative), such that ``a == U S Vh``, where ``S`` is the diagonal matrix ``np.diag(s)``. Parameters ---------- a : array_like, shape (M, N) Matrix to decompose full_matrices : boolean, optional If True (default), ``U`` and ``Vh`` are shaped ``(M,M)`` and ``(N,N)``. Otherwise, the shapes are ``(M,K)`` and ``(K,N)``, where ``K = min(M,N)``. compute_uv : boolean Whether to compute ``U`` and ``Vh`` in addition to ``s``. True by default. Returns ------- U : ndarray, shape (M, M) or (M, K) depending on `full_matrices` Unitary matrix. s : ndarray, shape (K,) where ``K = min(M, N)`` The singular values, sorted so that ``s[i] >= s[i+1]``. Vh : ndarray, shape (N,N) or (K,N) depending on `full_matrices` Unitary matrix. Raises ------ LinAlgError If SVD computation does not converge. Notes ----- If `a` is a matrix (in contrast to an ndarray), then so are all the return values. Examples -------- >>> a = np.random.randn(9, 6) + 1j*np.random.randn(9, 6) >>> U, s, Vh = np.linalg.svd(a) >>> U.shape, Vh.shape, s.shape ((9, 9), (6, 6), (6,)) >>> U, s, Vh = np.linalg.svd(a, full_matrices=False) >>> U.shape, Vh.shape, s.shape ((9, 6), (6, 6), (6,)) >>> S = np.diag(s) >>> np.allclose(a, np.dot(U, np.dot(S, Vh))) True >>> s2 = np.linalg.svd(a, compute_uv=False) >>> np.allclose(s, s2) True """ a, wrap = _makearray(a) _assertRank2(a) _assertNonEmpty(a) m, n = a.shape t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) s = zeros((min(n, m),), real_t) if compute_uv: if full_matrices: nu = m nvt = n option = 'A' else: nu = min(n, m) nvt = min(n, m) option = 'S' u = zeros((nu, m), t) vt = zeros((n, nvt), t) else: option = 'N' nu = 1 nvt = 1 u = empty((1, 1), t) vt = empty((1, 1), t) iwork = zeros((8*min(m, n),), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zgesdd rwork = zeros((5*min(m, n)*min(m, n) + 5*min(m, n),), real_t) lwork = 1 work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, -1, rwork, iwork, 0) lwork = int(abs(work[0])) work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, lwork, rwork, iwork, 0) else: lapack_routine = lapack_lite.dgesdd lwork = 1 work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, -1, iwork, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, lwork, iwork, 0) if results['info'] > 0: raise LinAlgError, 'SVD did not converge' s = s.astype(_realType(result_t)) if compute_uv: u = u.transpose().astype(result_t) vt = vt.transpose().astype(result_t) return wrap(u), s, wrap(vt) else: return s
def svd_zgesvd(a, full_matrices=1, compute_uv=1): """ Singular Value Decomposition of a complex matrix. Factorizes the matrix `a` into two unitary matrices, ``U`` and ``Vh``, and a 1-dimensional array of singular values, ``s`` (real, non-negative), such that ``a == U S Vh``, where ``S`` is the diagonal matrix ``np.diag(s)``. Parameters ---------- a : array_like, shape (M, N) Matrix to decompose full_matrices : boolean, optional If True (default), ``U`` and ``Vh`` are shaped ``(M,M)`` and ``(N,N)``. Otherwise, the shapes are ``(M,K)`` and ``(K,N)``, where ``K = min(M,N)``. compute_uv : boolean Whether to compute ``U`` and ``Vh`` in addition to ``s``. True by default. Returns ------- U : ndarray, shape (M, M) or (M, K) depending on `full_matrices` Unitary matrix. s : ndarray, shape (K,) where ``K = min(M, N)`` The singular values, sorted so that ``s[i] >= s[i+1]``. Vh : ndarray, shape (N,N) or (K,N) depending on `full_matrices` Unitary matrix. Raises ------ LinAlgError If SVD computation fails. For details see zgesvd.f and dbdsqr.f of LAPACK """ a, wrap = _makearray(a) _assertRank2(a) _assertNonEmpty(a) m, n = a.shape t, result_t = _commonType(a) real_t = _linalgRealType(t) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) s = zeros((min(n, m),), real_t) if compute_uv: if full_matrices: nu = m nvt = n option = "A" else: nu = min(n, m) nvt = min(n, m) option = "S" u = zeros((nu, m), t) vt = zeros((n, nvt), t) else: option = "N" nu = 1 nvt = 1 u = empty((1, 1), t) vt = empty((1, 1), t) lapack_routine = lib.zgesvd_ lwork = 1 work = zeros((lwork,), t) INFO = c_int(0) m = c_int(m) n = c_int(n) nvt = c_int(nvt) lwork = c_int(-1) K = min(a.shape) rwork = zeros((5 * K,), real_t) lapack_routine(option, option, m, n, a, m, s, u, m, vt, nvt, work, lwork, rwork, INFO) if INFO.value < 0: raise Exception("%d-th argument had an illegal value" % INFO.value) lwork = int(work[0].real) work = zeros((lwork,), t) lwork = c_int(lwork) rwork = zeros((5 * K,), real_t) lapack_routine(option, option, m, n, a, m, s, u, m, vt, nvt, work, lwork, rwork, INFO) if INFO.value > 0: raise Exception("Error during factorization: %d" % INFO.value) # raise LinAlgError, 'SVD did not converge' s = s.astype(_realType(result_t)) if compute_uv: u = u.transpose().astype(result_t) vt = vt.transpose().astype(result_t) return wrap(u), s, wrap(vt) else: return s
def lstsq(a, b, rcond=-1): """ Return the least-squares solution to an equation. Solves the equation `a x = b` by computing a vector `x` that minimizes the norm `|| b - a x ||`. Parameters ---------- a : array_like, shape (M, N) Input equation coefficients. b : array_like, shape (M,) or (M, K) Equation target values. If `b` is two-dimensional, the least squares solution is calculated for each of the `K` target sets. rcond : float, optional Cutoff for ``small`` singular values of `a`. Singular values smaller than `rcond` times the largest singular value are considered zero. Returns ------- x : ndarray, shape(N,) or (N, K) Least squares solution. The shape of `x` depends on the shape of `b`. residues : ndarray, shape(), (1,), or (K,) Sums of residues; squared Euclidian norm for each column in `b - a x`. If the rank of `a` is < N or > M, this is an empty array. If `b` is 1-dimensional, this is a (1,) shape array. Otherwise the shape is (K,). rank : integer Rank of matrix `a`. s : ndarray, shape(min(M,N),) Singular values of `a`. Raises ------ LinAlgError If computation does not converge. Notes ----- If `b` is a matrix, then all array results returned as matrices. Examples -------- Fit a line, ``y = mx + c``, through some noisy data-points: >>> x = np.array([0, 1, 2, 3]) >>> y = np.array([-1, 0.2, 0.9, 2.1]) By examining the coefficients, we see that the line should have a gradient of roughly 1 and cuts the y-axis at more-or-less -1. We can rewrite the line equation as ``y = Ap``, where ``A = [[x 1]]`` and ``p = [[m], [c]]``. Now use `lstsq` to solve for `p`: >>> A = np.vstack([x, np.ones(len(x))]).T >>> A array([[ 0., 1.], [ 1., 1.], [ 2., 1.], [ 3., 1.]]) >>> m, c = np.linalg.lstsq(A, y)[0] >>> print m, c 1.0 -0.95 Plot the data along with the fitted line: >>> import matplotlib.pyplot as plt >>> plt.plot(x, y, 'o', label='Original data', markersize=10) >>> plt.plot(x, m*x + c, 'r', label='Fitted line') >>> plt.legend() >>> plt.show() """ import math a, _ = _makearray(a) b, wrap = _makearray(b) is_1d = len(b.shape) == 1 if is_1d: b = b[:, newaxis] _assertRank2(a, b) m = a.shape[0] n = a.shape[1] n_rhs = b.shape[1] ldb = max(n, m) if m != b.shape[0]: raise LinAlgError, 'Incompatible dimensions' t, result_t = _commonType(a, b) real_t = _linalgRealType(t) bstar = zeros((ldb, n_rhs), t) bstar[:b.shape[0],:n_rhs] = b.copy() a, bstar = _fastCopyAndTranspose(t, a, bstar) s = zeros((min(m, n),), real_t) nlvl = max( 0, int( math.log( float(min(m, n))/2. ) ) + 1 ) iwork = zeros((3*min(m, n)*nlvl+11*min(m, n),), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zgelsd lwork = 1 rwork = zeros((lwork,), real_t) work = zeros((lwork,), t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, -1, rwork, iwork, 0) lwork = int(abs(work[0])) rwork = zeros((lwork,), real_t) a_real = zeros((m, n), real_t) bstar_real = zeros((ldb, n_rhs,), real_t) results = lapack_lite.dgelsd(m, n, n_rhs, a_real, m, bstar_real, ldb, s, rcond, 0, rwork, -1, iwork, 0) lrwork = int(rwork[0]) work = zeros((lwork,), t) rwork = zeros((lrwork,), real_t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, lwork, rwork, iwork, 0) else: lapack_routine = lapack_lite.dgelsd lwork = 1 work = zeros((lwork,), t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, -1, iwork, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, lwork, iwork, 0) if results['info'] > 0: raise LinAlgError, 'SVD did not converge in Linear Least Squares' resids = array([], t) if is_1d: x = array(ravel(bstar)[:n], dtype=result_t, copy=True) if results['rank'] == n and m > n: resids = array([sum((ravel(bstar)[n:])**2)], dtype=result_t) else: x = array(transpose(bstar)[:n,:], dtype=result_t, copy=True) if results['rank'] == n and m > n: resids = sum((transpose(bstar)[n:,:])**2, axis=0).astype(result_t) st = s[:min(n, m)].copy().astype(_realType(result_t)) return wrap(x), wrap(resids), results['rank'], st
def svd(a, full_matrices=1, compute_uv=1): """Singular Value Decomposition. Factorizes the matrix a into two unitary matrices U and Vh and an 1d-array s of singular values (real, non-negative) such that a == U S Vh if S is an suitably shaped matrix of zeros whose main diagonal is s. Parameters ---------- a : array-like, shape (M, N) Matrix to decompose full_matrices : boolean If true, U, Vh are shaped (M,M), (N,N) If false, the shapes are (M,K), (K,N) where K = min(M,N) compute_uv : boolean Whether to compute U and Vh in addition to s Returns ------- U: array, shape (M,M) or (M,K) depending on full_matrices s: array, shape (K,) The singular values, sorted so that s[i] >= s[i+1] K = min(M, N) Vh: array, shape (N,N) or (K,N) depending on full_matrices If a is a matrix, so are all the return values. Raises LinAlgError if SVD computation does not converge Examples -------- >>> a = random.randn(9, 6) + 1j*random.randn(9, 6) >>> U, s, Vh = linalg.svd(a) >>> U.shape, Vh.shape, s.shape ((9, 9), (6, 6), (6,)) >>> U, s, Vh = linalg.svd(a, full_matrices=False) >>> U.shape, Vh.shape, s.shape ((9, 6), (6, 6), (6,)) >>> S = diag(s) >>> allclose(a, dot(U, dot(S, Vh))) True >>> s2 = linalg.svd(a, compute_uv=False) >>> allclose(s, s2) True """ a, wrap = _makearray(a) _assertRank2(a) _assertNonEmpty(a) m, n = a.shape t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) s = zeros((min(n, m),), real_t) if compute_uv: if full_matrices: nu = m nvt = n option = 'A' else: nu = min(n, m) nvt = min(n, m) option = 'S' u = zeros((nu, m), t) vt = zeros((n, nvt), t) else: option = 'N' nu = 1 nvt = 1 u = empty((1, 1), t) vt = empty((1, 1), t) iwork = zeros((8*min(m, n),), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zgesdd rwork = zeros((5*min(m, n)*min(m, n) + 5*min(m, n),), real_t) lwork = 1 work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, -1, rwork, iwork, 0) lwork = int(abs(work[0])) work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, lwork, rwork, iwork, 0) else: lapack_routine = lapack_lite.dgesdd lwork = 1 work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, -1, iwork, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, lwork, iwork, 0) if results['info'] > 0: raise LinAlgError, 'SVD did not converge' s = s.astype(_realType(result_t)) if compute_uv: u = u.transpose().astype(result_t) vt = vt.transpose().astype(result_t) return wrap(u), s, wrap(vt) else: return s
def qr(a, mode='full'): """ Compute QR decomposition of a matrix. Calculate the decomposition :math:`A = Q R` where Q is orthonormal and R upper triangular. Parameters ---------- a : array_like, shape (M, N) Matrix to be decomposed mode : {'full', 'r', 'economic'} Determines what information is to be returned. 'full' is the default. Economic mode is slightly faster if only R is needed. Returns ------- mode = 'full' Q : double or complex array, shape (M, K) R : double or complex array, shape (K, N) Size K = min(M, N) mode = 'r' R : double or complex array, shape (K, N) mode = 'economic' A2 : double or complex array, shape (M, N) The diagonal and the upper triangle of A2 contains R, while the rest of the matrix is undefined. If a is a matrix, so are all the return values. Raises LinAlgError if decomposition fails Notes ----- This is an interface to the LAPACK routines dgeqrf, zgeqrf, dorgqr, and zungqr. Examples -------- >>> a = np.random.randn(9, 6) >>> q, r = np.linalg.qr(a) >>> np.allclose(a, np.dot(q, r)) True >>> r2 = np.linalg.qr(a, mode='r') >>> r3 = np.linalg.qr(a, mode='economic') >>> np.allclose(r, r2) True >>> np.allclose(r, np.triu(r3[:6,:6], k=0)) True """ a, wrap = _makearray(a) _assertRank2(a) m, n = a.shape t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) mn = min(m, n) tau = zeros((mn,), t) if isComplexType(t): lapack_routine = lapack_lite.zgeqrf routine_name = 'zgeqrf' else: lapack_routine = lapack_lite.dgeqrf routine_name = 'dgeqrf' # calculate optimal size of work data 'work' lwork = 1 work = zeros((lwork,), t) results = lapack_routine(m, n, a, m, tau, work, -1, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) # do qr decomposition lwork = int(abs(work[0])) work = zeros((lwork,), t) results = lapack_routine(m, n, a, m, tau, work, lwork, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) # economic mode. Isn't actually economic. if mode[0] == 'e': if t != result_t : a = a.astype(result_t) return a.T # generate r r = _fastCopyAndTranspose(result_t, a[:,:mn]) for i in range(mn): r[i,:i].fill(0.0) # 'r'-mode, that is, calculate only r if mode[0] == 'r': return r # from here on: build orthonormal matrix q from a if isComplexType(t): lapack_routine = lapack_lite.zungqr routine_name = 'zungqr' else: lapack_routine = lapack_lite.dorgqr routine_name = 'dorgqr' # determine optimal lwork lwork = 1 work = zeros((lwork,), t) results = lapack_routine(m, mn, mn, a, m, tau, work, -1, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) # compute q lwork = int(abs(work[0])) work = zeros((lwork,), t) results = lapack_routine(m, mn, mn, a, m, tau, work, lwork, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) q = _fastCopyAndTranspose(result_t, a[:mn,:]) return wrap(q), wrap(r)
def svd(a, full_matrices=1, compute_uv=1): """ Singular Value Decomposition. Factorizes the matrix `a` into two unitary matrices, ``U`` and ``Vh``, and a 1-dimensional array of singular values, ``s`` (real, non-negative), such that ``a == U S Vh``, where ``S`` is the diagonal matrix ``np.diag(s)``. Parameters ---------- a : array_like, shape (M, N) Matrix to decompose full_matrices : boolean, optional If True (default), ``U`` and ``Vh`` are shaped ``(M,M)`` and ``(N,N)``. Otherwise, the shapes are ``(M,K)`` and ``(K,N)``, where ``K = min(M,N)``. compute_uv : boolean Whether to compute ``U`` and ``Vh`` in addition to ``s``. True by default. Returns ------- U : ndarray, shape (M, M) or (M, K) depending on `full_matrices` Unitary matrix. s : ndarray, shape (K,) where ``K = min(M, N)`` The singular values, sorted so that ``s[i] >= s[i+1]``. Vh : ndarray, shape (N,N) or (K,N) depending on `full_matrices` Unitary matrix. Raises ------ LinAlgError If SVD computation does not converge. Notes ----- If `a` is a matrix (in contrast to an ndarray), then so are all the return values. Examples -------- >>> a = np.random.randn(9, 6) + 1j*np.random.randn(9, 6) >>> U, s, Vh = np.linalg.svd(a) >>> U.shape, Vh.shape, s.shape ((9, 9), (6, 6), (6,)) >>> U, s, Vh = np.linalg.svd(a, full_matrices=False) >>> U.shape, Vh.shape, s.shape ((9, 6), (6, 6), (6,)) >>> S = np.diag(s) >>> np.allclose(a, np.dot(U, np.dot(S, Vh))) True >>> s2 = np.linalg.svd(a, compute_uv=False) >>> np.allclose(s, s2) True """ a, wrap = _makearray(a) _assertRank2(a) _assertNonEmpty(a) m, n = a.shape t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) s = zeros((min(n, m), ), real_t) if compute_uv: if full_matrices: nu = m nvt = n option = 'A' else: nu = min(n, m) nvt = min(n, m) option = 'S' u = zeros((nu, m), t) vt = zeros((n, nvt), t) else: option = 'N' nu = 1 nvt = 1 u = empty((1, 1), t) vt = empty((1, 1), t) iwork = zeros((8 * min(m, n), ), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zgesdd rwork = zeros((5 * min(m, n) * min(m, n) + 5 * min(m, n), ), real_t) lwork = 1 work = zeros((lwork, ), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, -1, rwork, iwork, 0) lwork = int(abs(work[0])) work = zeros((lwork, ), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, lwork, rwork, iwork, 0) else: lapack_routine = lapack_lite.dgesdd lwork = 1 work = zeros((lwork, ), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, -1, iwork, 0) lwork = int(work[0]) work = zeros((lwork, ), t) results = lapack_routine(option, m, n, a, m, s, u, m, vt, nvt, work, lwork, iwork, 0) if results['info'] > 0: raise LinAlgError, 'SVD did not converge' s = s.astype(_realType(result_t)) if compute_uv: u = u.transpose().astype(result_t) vt = vt.transpose().astype(result_t) return wrap(u), s, wrap(vt) else: return s
def qr(a, mode='full'): """ Compute QR decomposition of a matrix. Calculate the decomposition :math:`A = Q R` where Q is orthonormal and R upper triangular. Parameters ---------- a : array_like, shape (M, N) Matrix to be decomposed mode : {'full', 'r', 'economic'} Determines what information is to be returned. 'full' is the default. Economic mode is slightly faster if only R is needed. Returns ------- mode = 'full' Q : double or complex array, shape (M, K) R : double or complex array, shape (K, N) Size K = min(M, N) mode = 'r' R : double or complex array, shape (K, N) mode = 'economic' A2 : double or complex array, shape (M, N) The diagonal and the upper triangle of A2 contains R, while the rest of the matrix is undefined. If a is a matrix, so are all the return values. Raises LinAlgError if decomposition fails Notes ----- This is an interface to the LAPACK routines dgeqrf, zgeqrf, dorgqr, and zungqr. Examples -------- >>> a = np.random.randn(9, 6) >>> q, r = np.linalg.qr(a) >>> np.allclose(a, np.dot(q, r)) True >>> r2 = np.linalg.qr(a, mode='r') >>> r3 = np.linalg.qr(a, mode='economic') >>> np.allclose(r, r2) True >>> np.allclose(r, np.triu(r3[:6,:6], k=0)) True """ a, wrap = _makearray(a) _assertRank2(a) m, n = a.shape t, result_t = _commonType(a) a = _fastCopyAndTranspose(t, a) mn = min(m, n) tau = zeros((mn, ), t) if isComplexType(t): lapack_routine = lapack_lite.zgeqrf routine_name = 'zgeqrf' else: lapack_routine = lapack_lite.dgeqrf routine_name = 'dgeqrf' # calculate optimal size of work data 'work' lwork = 1 work = zeros((lwork, ), t) results = lapack_routine(m, n, a, m, tau, work, -1, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) # do qr decomposition lwork = int(abs(work[0])) work = zeros((lwork, ), t) results = lapack_routine(m, n, a, m, tau, work, lwork, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) # economic mode. Isn't actually economic. if mode[0] == 'e': if t != result_t: a = a.astype(result_t) return a.T # generate r r = _fastCopyAndTranspose(result_t, a[:, :mn]) for i in range(mn): r[i, :i].fill(0.0) # 'r'-mode, that is, calculate only r if mode[0] == 'r': return r # from here on: build orthonormal matrix q from a if isComplexType(t): lapack_routine = lapack_lite.zungqr routine_name = 'zungqr' else: lapack_routine = lapack_lite.dorgqr routine_name = 'dorgqr' # determine optimal lwork lwork = 1 work = zeros((lwork, ), t) results = lapack_routine(m, mn, mn, a, m, tau, work, -1, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) # compute q lwork = int(abs(work[0])) work = zeros((lwork, ), t) results = lapack_routine(m, mn, mn, a, m, tau, work, lwork, 0) if results['info'] != 0: raise LinAlgError, '%s returns %d' % (routine_name, results['info']) q = _fastCopyAndTranspose(result_t, a[:mn, :]) return wrap(q), wrap(r)
def lstsq(a, b, rcond=-1): """Compute least-squares solution to equation :math:`a x = b` Compute a vector x such that the 2-norm :math:`|b - a x|` is minimised. Parameters ---------- a : array-like, shape (M, N) b : array-like, shape (M,) or (M, K) rcond : float Cutoff for 'small' singular values. Singular values smaller than rcond*largest_singular_value are considered zero. Raises LinAlgError if computation does not converge Returns ------- x : array, shape (N,) or (N, K) depending on shape of b Least-squares solution residues : array, shape () or (1,) or (K,) Sums of residues, squared 2-norm for each column in :math:`b - a x` If rank of matrix a is < N or > M this is an empty array. If b was 1-d, this is an (1,) shape array, otherwise the shape is (K,) rank : integer Rank of matrix a s : array, shape (min(M,N),) Singular values of a If b is a matrix, then all results except the rank are also returned as matrices. """ import math a, _ = _makearray(a) b, wrap = _makearray(b) is_1d = len(b.shape) == 1 if is_1d: b = b[:, newaxis] _assertRank2(a, b) m = a.shape[0] n = a.shape[1] n_rhs = b.shape[1] ldb = max(n, m) if m != b.shape[0]: raise LinAlgError, 'Incompatible dimensions' t, result_t = _commonType(a, b) real_t = _linalgRealType(t) bstar = zeros((ldb, n_rhs), t) bstar[:b.shape[0],:n_rhs] = b.copy() a, bstar = _fastCopyAndTranspose(t, a, bstar) s = zeros((min(m, n),), real_t) nlvl = max( 0, int( math.log( float(min(m, n))/2. ) ) + 1 ) iwork = zeros((3*min(m, n)*nlvl+11*min(m, n),), fortran_int) if isComplexType(t): lapack_routine = lapack_lite.zgelsd lwork = 1 rwork = zeros((lwork,), real_t) work = zeros((lwork,), t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, -1, rwork, iwork, 0) lwork = int(abs(work[0])) rwork = zeros((lwork,), real_t) a_real = zeros((m, n), real_t) bstar_real = zeros((ldb, n_rhs,), real_t) results = lapack_lite.dgelsd(m, n, n_rhs, a_real, m, bstar_real, ldb, s, rcond, 0, rwork, -1, iwork, 0) lrwork = int(rwork[0]) work = zeros((lwork,), t) rwork = zeros((lrwork,), real_t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, lwork, rwork, iwork, 0) else: lapack_routine = lapack_lite.dgelsd lwork = 1 work = zeros((lwork,), t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, -1, iwork, 0) lwork = int(work[0]) work = zeros((lwork,), t) results = lapack_routine(m, n, n_rhs, a, m, bstar, ldb, s, rcond, 0, work, lwork, iwork, 0) if results['info'] > 0: raise LinAlgError, 'SVD did not converge in Linear Least Squares' resids = array([], t) if is_1d: x = array(ravel(bstar)[:n], dtype=result_t, copy=True) if results['rank'] == n and m > n: resids = array([sum((ravel(bstar)[n:])**2)], dtype=result_t) else: x = array(transpose(bstar)[:n,:], dtype=result_t, copy=True) if results['rank'] == n and m > n: resids = sum((transpose(bstar)[n:,:])**2, axis=0).astype(result_t) st = s[:min(n, m)].copy().astype(_realType(result_t)) return wrap(x), wrap(resids), results['rank'], st
def svd_dgesvd(a, full_matrices=1, compute_uv=1): """ Singular Value Decomposition. Factorizes the matrix `a` into two unitary matrices, ``U`` and ``Vh``, and a 1-dimensional array of singular values, ``s`` (real, non-negative), such that ``a == U S Vh``, where ``S`` is the diagonal matrix ``np.diag(s)``. Parameters ---------- a : array_like, shape (M, N) Matrix to decompose full_matrices : boolean, optional If True (default), ``U`` and ``Vh`` are shaped ``(M,M)`` and ``(N,N)``. Otherwise, the shapes are ``(M,K)`` and ``(K,N)``, where ``K = min(M,N)``. compute_uv : boolean Whether to compute ``U`` and ``Vh`` in addition to ``s``. True by default. Returns ------- U : ndarray, shape (M, M) or (M, K) depending on `full_matrices` Unitary matrix. s : ndarray, shape (K,) where ``K = min(M, N)`` The singular values, sorted so that ``s[i] >= s[i+1]``. Vh : ndarray, shape (N,N) or (K,N) depending on `full_matrices` Unitary matrix. Raises ------ LinAlgError If SVD computation fails. For details see dgesvd.f and dbdsqr.f of LAPACK """ a, wrap = _makearray(a) _assertRank2(a) _assertNonEmpty(a) m, n = a.shape t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) s = zeros((min(n, m),), real_t) if compute_uv: if full_matrices: nu = m nvt = n option = 'A' else: nu = min(n, m) nvt = min(n, m) option = 'S' u = zeros((nu, m), t) vt = zeros((n, nvt), t) else: option = 'N' nu = 1 nvt = 1 u = empty((1, 1), t) vt = empty((1, 1), t) lapack_routine = lib.dgesvd_ lwork = 1 work = zeros((lwork,), t) INFO = c_int(0) m = c_int(m) n = c_int(n) nvt = c_int(nvt) lwork = c_int(-1) lapack_routine(option, option, m, n, a, m, s, u, m, vt, nvt, work, lwork, INFO) if INFO.value < 0: raise Exception('%d-th argument had an illegal value' % INFO.value) lwork = int(work[0]) work = zeros((lwork,), t) lwork = c_int(lwork) lapack_routine(option, option, m, n, a, m, s, u, m, vt, nvt, work, lwork, INFO) if INFO.value > 0: raise Exception('Error during factorization: %d' % INFO.value) # raise LinAlgError, 'SVD did not converge' s = s.astype(_realType(result_t)) if compute_uv: u = u.transpose().astype(result_t) vt = vt.transpose().astype(result_t) return wrap(u), s, wrap(vt) else: return s
def eigvals(a): """ Compute the eigenvalues of a general matrix. Parameters ---------- a : array_like, shape (M, M) A complex or real matrix whose eigenvalues and eigenvectors will be computed. Returns ------- w : ndarray, shape (M,) The eigenvalues, each repeated according to its multiplicity. They are not necessarily ordered, nor are they necessarily real for real matrices. Raises ------ LinAlgError If the eigenvalue computation does not converge. See Also -------- eig : eigenvalues and right eigenvectors of general arrays eigvalsh : eigenvalues of symmetric or Hemitiean arrays. eigh : eigenvalues and eigenvectors of symmetric/Hermitean arrays. Notes ----- This is a simple interface to the LAPACK routines dgeev and zgeev that sets the flags to return only the eigenvalues of general real and complex arrays respectively. The number w is an eigenvalue of a if there exists a vector v satisfying the equation dot(a,v) = w*v. Alternately, if w is a root of the characteristic equation det(a - w[i]*I) = 0, where det is the determinant and I is the identity matrix. """ a, wrap = _makearray(a) _assertRank2(a) _assertSquareness(a) _assertFinite(a) t, result_t = _commonType(a) real_t = _linalgRealType(t) a = _fastCopyAndTranspose(t, a) n = a.shape[0] dummy = zeros((1, ), t) if isComplexType(t): lapack_routine = lapack_lite.zgeev w = zeros((n, ), t) rwork = zeros((n, ), real_t) lwork = 1 work = zeros((lwork, ), t) results = lapack_routine('N', 'N', n, a, n, w, dummy, 1, dummy, 1, work, -1, rwork, 0) lwork = int(abs(work[0])) work = zeros((lwork, ), t) results = lapack_routine('N', 'N', n, a, n, w, dummy, 1, dummy, 1, work, lwork, rwork, 0) else: lapack_routine = lapack_lite.dgeev wr = zeros((n, ), t) wi = zeros((n, ), t) lwork = 1 work = zeros((lwork, ), t) results = lapack_routine('N', 'N', n, a, n, wr, wi, dummy, 1, dummy, 1, work, -1, 0) lwork = int(work[0]) work = zeros((lwork, ), t) results = lapack_routine('N', 'N', n, a, n, wr, wi, dummy, 1, dummy, 1, work, lwork, 0) if all(wi == 0.): w = wr result_t = _realType(result_t) else: w = wr + 1j * wi result_t = _complexType(result_t) if results['info'] > 0: raise LinAlgError, 'Eigenvalues did not converge' return w.astype(result_t)