0

I am new to this Forum. I have recently started learning c++ as it is required for my work. I have installed GSL library and BLAS on Ubuntu 12.04. I have written code to compute matrix exponential, which works fine with the gsl library. I now have written c++ code to invert a complex matrix. This seems to be tricky. I first need to call a gsl function gsl_linalg_complex_LU_decomp() to define decomposition of the matrix and then call another gsl function to compute the matrix inverse. However, the program, which is given below, does not compile on Ubuntu 12.04. I am using the command

g++ MatInv.cpp -o MatInv.exe -lgsl -llapack.

The output error on the terminal is:

/tmp/ccUVd80t.o: In function `main':MatInv.cpp.text+0x638): undefined reference to `gsl_linalg_complex_LU_decomp_'
collect2: ld returned 1 exit status

I have searched the net for this problem but can't seem to find the right answer to my problem. The code is as follows (again, I am new to c++, so you might find this to be a very primitive way to code.) Here I am only computing the decomposition of the matrix. Please let me know what is wrong here. Thanks for your help.

#include <iostream>
#include <gsl/gsl_matrix_complex_double.h>
#include <gsl/gsl_linalg.h>
#include <gsl/gsl_complex.h>
#include <gsl/gsl_complex_math.h>
#include <gsl/gsl_cblas.h>
#include <gsl/gsl_matrix.h>
#include <cmath>
#include <complex>
#include <fstream>


using namespace::std;


typedef complex<double> cd;


extern "C" int gsl_linalg_complex_LU_decomp_(gsl_matrix_complex *A, gsl_permutation *p, int signum);


//**************************************************************************


int main()
{


//Here we define matrix A


int dimA=3;          //dimensions of the matrix A
cd im(0.,1.),u(1.,0.);
cd **A,**B; 
A= new cd *[dimA];
B= new cd *[dimA];



for(int i=0; i<dimA; i++){ 
 A[i]= new cd [dimA];
 B[i]= new cd [dimA];
}


for(int i=0; i< dimA; i++){ // Initializing the matrix 
 for(int j=0; j<dimA; j++){
  A[i][j]=(0.,0.);
  B[i][j]=(0.,0.);
 }
}


ofstream Lmat;
Lmat.open("Mat.dat");
for(int i=0; i< dimA; i++){
 for(int j=0; j< dimA; j++){
  if(i==j)A[i][j]=.1*(i+1)*u+.2*(j+1)*u;
  else A[i][j]=.1*(i+1)*u+.2*(j+1)*im;
  Lmat<<A[i][j];
 }
 Lmat<<endl;
}


Lmat.close();


gsl_matrix_complex *gsl_A= gsl_matrix_complex_calloc(dimA,dimA);


for(int i=0;i<dimA;i++){
 for(int j=0;j<dimA;j++){
  double A_elem_re = A[i][j].real();
  double A_elem_im = A[i][j].imag();
    gsl_matrix_complex_set(gsl_A,i,j,gsl_complex_rect(A_elem_re,A_elem_im));
 }
} 


gsl_permutation *p=gsl_permutation_alloc(dimA);
int signum;


gsl_linalg_complex_LU_decomp_(gsl_A, p, signum);




 gsl_permutation_free (p);


 return 0;
}
Simon Gibbons
  • 6,969
  • 1
  • 21
  • 34
OPP
  • 1

1 Answers1

0

There are a couple of problems here.

Firstly you don't need to declare the function gsl_linalg_complex_LU_decomp so you can get rid of the line

extern "C" int gsl_linalg_complex_LU_decomp_(gsl_matrix_complex *A, gsl_permutation *p, int signum);

Secondly when you call this function later on you have a couple of problems, firstly you need have an errant underscore in it's name so get rid of that and secondly the parameter signum needs to be an int * (i.e. a pointer to an int) not an int as you are doing currently.

If you replace that line with

gsl_linalg_complex_LU_decomp(gsl_A, p, &signum);

your code should compile fine.

Simon Gibbons
  • 6,969
  • 1
  • 21
  • 34
  • Thanks, Simon. It works just fine!:-) But I am just wondering, in my other codes I have underscores while caling GSL functions and it works all right. In fact I read somewhere that this is needed to call a Fortran subroutine from a c++ code. Is that right? Thanks again. I wasted two days in this. :-( – OPP Apr 17 '15 at 15:01