view liboctave/numeric/gsvd.h @ 22236:065a44375723

gsvd: reduce code duplication with templates. * CmplxGSVD.cc, CmplxGSVD.h, dbleGSVD.cc, dbleGSVD.h: Remove files for no longer existing classes. Replaced by gsvd template class. This classes never existed in an Octave release, this was freshly imported from Octave Forge so backwards compatibility is not an issue. * liboctave/numeric/gsvd.h, liboctave/numeric/gsvd.cc: New files for gsvd class template generated from CmplxGSVD.cc, CmplxGSVD.h, dbleGSVD.cc, and dbleGSVD.h and converted to template. Removed unused << operator, unused constructor with &info, and commented code. Only instantiated for Matrix and ComplexMatrix, providing interface to DGGSVD and ZGGSVD. * liboctave/numeric/module.mk: Update. * mx-defs.h, mx-ext.h: Use new classes.
author Barbara Locsi <locsi.barbara@gmail.com>
date Tue, 09 Aug 2016 18:02:11 +0200
parents
children bac0d6f07a3e
line wrap: on
line source

// Copyright (C) 1996, 1997 John W. Eaton
// Copyright (C) 2006 Pascal Dupuis <Pascal.Dupuis@uclouvain.be>
// Copyright (C) 2016 Barbara Lócsi
//
// This program is free software; you can redistribute it and/or modify it under
// the terms of the GNU General Public License as published by the Free Software
// Foundation; either version 3 of the License, or (at your option) any later
// version.
//
// This program is distributed in the hope that it will be useful, but WITHOUT
// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
// details.
//
// You should have received a copy of the GNU General Public License along with
// this program; if not, see <http://www.gnu.org/licenses/>.

#if !defined (octave_gsvd_h)
#define octave_gsvd_h 1

#include "octave-config.h"

#include "dDiagMatrix.h"
#include "dMatrix.h"

template <typename T>
class
gsvd
{
public:

  enum class Type
  {
    std,
    economy,
    sigma_only
  };

  gsvd (void) : sigmaA (), sigmaB (), left_smA (), left_smB (), right_sm () { }

  gsvd (const T& a, const T& b, gsvd::Type gsvd_type = gsvd<T>::Type::economy);

  gsvd (const gsvd& a)
    : type (a.type),
      sigmaA (a.sigmaA), sigmaB (a.sigmaB),
      left_smA (a.left_smA), left_smB (a.left_smB), right_sm (a.right_sm),
      R(a.R) { }

  gsvd& operator = (const gsvd& a)
    {
      if (this != &a)
        {
          type = a.type;
          sigmaA = a.sigmaA;
          sigmaB = a.sigmaB;
          left_smA = a.left_smA;
          left_smB = a.left_smB;
          right_sm = a.right_sm;
          R = a.R;
        }

      return *this;
    }

  ~gsvd (void) { }

  DiagMatrix singular_values_A (void) const { return sigmaA; }
  DiagMatrix singular_values_B (void) const { return sigmaB; }

  T left_singular_matrix_A (void) const;
  T left_singular_matrix_B (void) const;

  T right_singular_matrix (void) const;
  T R_matrix (void) const;

private:

  gsvd::Type type;

  typedef typename T::element_type P;

  DiagMatrix sigmaA, sigmaB;
  T left_smA, left_smB;
  T right_sm, R;

  void ggsvd (char& jobu, char& jobv, char& jobq, octave_idx_type m,
              octave_idx_type n, octave_idx_type p, octave_idx_type& k,
              octave_idx_type& l, P *tmp_dataA, octave_idx_type m1,
              P *tmp_dataB, octave_idx_type p1, Matrix& alpha, Matrix& beta,
              P *u, octave_idx_type nrow_u, P *v, octave_idx_type nrow_v, P *q,
              octave_idx_type nrow_q, T& work, octave_idx_type* iwork,
              octave_idx_type& info);
};

#endif