使用带有代码块的armadillo时出错

时间:2014-05-27 12:52:23

标签: lapack armadillo

我在codeblocks中使用mingw编译器。 当我编译我的代码时,它编译得很完美。但是,当我运行它时,我收到以下错误。虽然我已经更改了config.hpp文件以启用Lapck,但仍然会出现此错误。另外使用#define ARMA_DONT_USE_WRAPPER也会出现同样的错误。

  

错误:svd():需要启用LAPACK使用

     

在抛出' std :: logic_error'
的实例后终止调用   what():svd():需要启用LAPACK使用

     

此应用程序已请求运行时将其终止   不寻常的方式请联系应用程序的支持团队获取更多信息   信息。

     

进程返回3(0x3)执行时间:4.227 s按任意键   继续。

以下是我的代码:

#include<fstream>
#include<sstream>
#include<iostream>
#include<conio.h>
#include<stdio.h>
#include<process.h>
#include<string>
#include<iomanip>
#include <random>
#include <math.h>
#define  ARMA_DONT_USE_WRAPPER
#include <armadillo>
#include <cstdio>
#include <cstdlib>


using namespace std;
using namespace arma;
//function to solve the nmf
double** pnmf(double** Xget, int row, int column)
{   int rows=row;
    int columns=column;
    int rinit=2;
    double X[rows][columns];
    for(int i = 0; i < rows; i++) {

        for(int j = 0; j < columns; j++){ X[i][j] = Xget[i][j]; }// sample set value;
    }
    // finding the transpose
    double Xt[columns][rows];
    for(int j=0; j<columns; j++) {
        for(int i=0; i<rows; i++){
            Xt[j][i]=X[i][j];
        }
    }

    int k=0;
    double XX[rows][columns];
    double r1[rows][rinit];
    double r2[rows][rinit];
    double r3[rinit][rinit];
    double r4[rows][rinit];
    double r5[rinit][rinit];
    double r6[rows][rinit];
    double r7[rows][rinit];
    double r8[rows][rinit];
    double r9[rows][rinit];
    double r10[rows][rinit];

      for(int i=0;i< rows;i++)
     {
          for(int j=0; j < columns ;j++)
          {
               XX[i][j] = 0;
          for(k=0;k< columns;k++)
          {
               XX[i][j] = XX[i][j] + X[i][k] * Xt[k][j];
          }
          } // end of j sub loop
     } // end of i main loop
    // initializing W;
    double W[rows][rinit];
    double Wt[rinit][rows];
    double W_Wold[rinit][rows];
    double Wold[rows][rinit];
    for(int i = 0; i < rows; ++i){
        for(int j = 0; j < rinit; j++){
            W[i][j] = (double)rand()/(double)RAND_MAX;
        }
    }

    int max_iter =100;
    double tol=0.00001;
    double sigma[rinit];
    double sigma_diag[rinit][rinit];
    double bsx[rows][rinit];

    for(int iter=0; iter<max_iter; iter++){
        // W_old
        for(int i = 0; i < rows; ++i){
        for(int j = 0; j < rinit; ++j){
            Wold[i][j] = W[i][j];
         }
       }
       mat B(rows,rinit);

       // calculate transpose of W
       for(int j=0; j<rinit; j++) {
        for(int i=0; i<rows; i++){
            Wt[j][i]=W[i][j];
        }
    }
        // calculate bsxfun
        for(int i = 0; i < rows; ++i){
        for(int j = 0; j < rinit; ++j){
            bsx[i][j] = W[i][j]*W[i][j];
         }
       }
       // calculate sigma
       for(int j = 0; j < rinit; ++j){
            sigma[j]=0;
        for(int i = 0; i < rows; ++i){
            sigma[j] = sigma[j]+bsx[i][j];
         }
       }
       //creating diagonal matrix of sigma
       for(int i = 0; i < rinit; ++i){
        for(int j = 0; j < rinit; ++j){
                if (i==j) {sigma_diag[i][j] = sigma[j];}
                else {sigma_diag[i][j] = 0; }
         }
       }
       // creating terms to update W
       for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
               r1[i][j] = 0;
          for(k=0;k< rows;k++)
          {
               r1[i][j] = r1[i][j] + XX[i][k] * W[k][j];
          }
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
               r2[i][j] = 0;
          for(k=0;k< rinit;k++)
          {
               r2[i][j] = r2[i][j] + r1[i][k] * sigma_diag[k][j];
          }
          } // end of j sub loop
     }
     for(int i=0;i< rinit; i++)
     {
          for(int j=0; j < rinit ;j++)
          {
               r3[i][j] = 0;
          for(k=0;k< rows;k++)
          {
               r3[i][j] = r3[i][j] + Wt[i][k] * r1[k][j];
          }
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
               r4[i][j] = 0;
          for(k=0;k< rinit; k++)
          {
               r4[i][j] = r4[i][j] + W[i][k] * r3[k][j];
          }
          } // end of j sub loop
     }
     for(int i=0;i< rinit;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
               r5[i][j] = 0;
          for(k=0;k< rows;k++)
          {
               r5[i][j] = r5[i][j] + Wt[i][k] * W[k][j];
          }
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
               r6[i][j] = 0;
          for(k=0;k< rinit;k++)
          {
               r6[i][j] = r6[i][j] + r1[i][k] * r5[k][j];
          }
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              r7[i][j]=r4[i][j]+r6[i][j];
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
               r8[i][j] = 0;
          for(k=0;k< rinit;k++)
          {
               r8[i][j] = r8[i][j] + r7[i][k] * sigma_diag[k][j];
          }
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              r9[i][j]=W[i][j]+r8[i][j];
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              r10[i][j]=r2[i][j]/r9[i][j];
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              W[i][j]=W[i][j]*r10[i][j];
          } // end of j sub loop
     }
     // finding norm of W
     //assigning W to A
     mat A(rows,rinit);
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              A(i,j) = W[i][j];
          } // end of j sub loop
     }

      double norm_W = norm(A);
     // final W
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              W[i][j]=W[i][j]/norm_W;
          } // end of j sub loop
     }

     //check convergence
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              W_Wold[i][j]=Wold[i][j] - W[i][j];
          } // end of j sub loop
     }
    // assigning W_Wold to B and W_old to A
    for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              A(i,j) = Wold[i][j];
          } // end of j sub loop
     }
     for(int i=0;i< rows;i++)
     {
          for(int j=0; j < rinit ;j++)
          {
              B(i,j) = W_Wold[i][j];
          } // end of j sub loop
     }
     double diffW= norm(B, "fro")/ norm(A, "fro");
     if (diffW<tol)
     {
         cout<<"\nconverged after"<<iter<<"steps";
         break;
     }
    }

    double** table = new double*[rows];
    for(int i = 0; i < rows; i++) {
        table[i] = new double[rinit];
        for(int j = 0; j < rinit; j++){ table[i][j] = W[i][j]; }// sample set value;
    }


    return table;
}

1 个答案:

答案 0 :(得分:0)

在Armadillo附带的README.txt文件中对此进行了解释。总之,请在ARMA_USE_LAPACK中启用include/armadillo_bits/config.hpp。换句话说,请确保取消注释config.hpp中的以下行:

#define ARMA_USE_LAPACK

或者,您也可以在代码中包含Armadillo标头之前声明上面的定义。例如:

#define  ARMA_DONT_USE_WRAPPER
#define  ARMA_USE_LAPACK
#include <armadillo>

然后,您需要与-llapack-lblas相关联,例如:

g++ prog.cpp -o prog -O2 -llapack -lblas