// This file is part of Eigen, a lightweight C++ template library
// for linear algebra.
//
// Copyright (C) 2014-2015 Gael Guennebaud <gael.guennebaud@inria.fr>
//
// This Source Code Form is subject to the terms of the Mozilla
// Public License v. 2.0. If a copy of the MPL was not distributed
// with this file, You can obtain one at http://mozilla.org/MPL/2.0/.

template<typename MatrixType>
void svd_fill_random(MatrixType &m, int Option = 0)
{
  using std::pow;
  typedef typename MatrixType::Scalar Scalar;
  typedef typename MatrixType::RealScalar RealScalar;
  typedef typename MatrixType::Index Index;
  Index diagSize = (std::min)(m.rows(), m.cols());
  RealScalar s = std::numeric_limits<RealScalar>::max_exponent10/4;
  s = internal::random<RealScalar>(1,s);
  Matrix<RealScalar,Dynamic,1> d =  Matrix<RealScalar,Dynamic,1>::Random(diagSize);
  for(Index k=0; k<diagSize; ++k)
    d(k) = d(k)*pow(RealScalar(10),internal::random<RealScalar>(-s,s));

  bool dup     = internal::random<int>(0,10) < 3;
  bool unit_uv = internal::random<int>(0,10) < (dup?7:3); // if we duplicate some diagonal entries, then increase the chance to preserve them using unitary U and V factors
  
  // duplicate some singular values
  if(dup)
  {
    Index n = internal::random<Index>(0,d.size()-1);
    for(Index i=0; i<n; ++i)
      d(internal::random<Index>(0,d.size()-1)) = d(internal::random<Index>(0,d.size()-1));
  }
  
  Matrix<Scalar,Dynamic,Dynamic> U(m.rows(),diagSize);
  Matrix<Scalar,Dynamic,Dynamic> VT(diagSize,m.cols());
  if(unit_uv)
  {
    // in very rare cases let's try with a pure diagonal matrix
    if(internal::random<int>(0,10) < 1)
    {
      U.setIdentity();
      VT.setIdentity();
    }
    else
    {
      createRandomPIMatrixOfRank(diagSize,U.rows(), U.cols(), U);
      createRandomPIMatrixOfRank(diagSize,VT.rows(), VT.cols(), VT);
    }
  }
  else
  {
    U.setRandom();
    VT.setRandom();
  }
  
  Matrix<Scalar,Dynamic,1> samples(9);
  samples << 0, 5.60844e-313, -5.60844e-313, 4.94e-324, -4.94e-324, -RealScalar(1)/NumTraits<RealScalar>::highest(), RealScalar(1)/NumTraits<RealScalar>::highest(), (std::numeric_limits<RealScalar>::min)(), pow((std::numeric_limits<RealScalar>::min)(),0.8);
  
  if(Option==Symmetric)
  {
    m = U * d.asDiagonal() * U.transpose();
    
    // randomly nullify some rows/columns
    {
      Index count = internal::random<Index>(-diagSize,diagSize);
      for(Index k=0; k<count; ++k)
      {
        Index i = internal::random<Index>(0,diagSize-1);
        m.row(i).setZero();
        m.col(i).setZero();
      }
      if(count<0)
      // (partly) cancel some coeffs
      if(!(dup && unit_uv))
      {
        
        Index n = internal::random<Index>(0,m.size()-1);
        for(Index k=0; k<n; ++k)
        {
          Index i = internal::random<Index>(0,m.rows()-1);
          Index j = internal::random<Index>(0,m.cols()-1);
          m(j,i) = m(i,j) = samples(internal::random<Index>(0,samples.size()-1));
          if(NumTraits<Scalar>::IsComplex)
            *(&numext::real_ref(m(j,i))+1) = *(&numext::real_ref(m(i,j))+1) = samples.real()(internal::random<Index>(0,samples.size()-1));
        }
      }
    }
  }
  else
  {
    m = U * d.asDiagonal() * VT;
    // (partly) cancel some coeffs
    if(!(dup && unit_uv))
    {
      Index n = internal::random<Index>(0,m.size()-1);
      for(Index k=0; k<n; ++k)
      {
        Index i = internal::random<Index>(0,m.rows()-1);
        Index j = internal::random<Index>(0,m.cols()-1);
        m(i,j) = samples(internal::random<Index>(0,samples.size()-1));
        if(NumTraits<Scalar>::IsComplex)
          *(&numext::real_ref(m(i,j))+1) = samples.real()(internal::random<Index>(0,samples.size()-1));
      }
    }
  }
}

