Hi,

I am using Sparselib++ in this C++ program.

#include <iostream>
#include <cstdlib>
#include "comprow_double.h"
using namespace std;

int main() {
	cout << "Sparse example" << endl; // prints Sparse example
	
	double val[12]={1,2,3,4,5,6,7,8,9,10,11,12};
	int colind[12]={0,1,4,0,1,2,1,2,4,3,0,4};
	int rowptr[6]={0,3,6,9,10,12};
	
	CompRow_Mat_double R (5,5,12,val,rowptr,colind);
	return 0;
}

Since I use Eclipse, I have added the -D preprocessor statement in the Project->Properties->C/C=++ Build->Settings->Preprocessor. The -D statement added here is

COMPLEX=std::complex<double>

which was given in the Sparselib++ makefile.def as

# g++ v. 2.7.0
#
CCC 			= g++
CC 				= gcc	
CCCFLAGS 	=  -DMV_VECTOR_BOUNDS_CHECK -g -Wall -pedantic\ 
     '-DCOMPLEX=std::complex<double>'  
CCCFLAGS 	=  -g -Wall -pedantic -O3 '-DCOMPLEX=std::complex<double>'  
LDFLAGS	= $(SPARSELIB_DIR)/lib/libsparse.a $(SPARSELIB_DIR)/lib/libspblas.a \
					$(SPARSELIB_DIR)/lib/libmv.a -lm

Now the build error I get is as follows saying " /bin/sh: double: No such file or directory'"

make -k all 
Building file: ../src/sparseCpp.cpp
/bin/sh: double: No such file or directory
Invoking: GCC C++ Compiler
g++ -DCOMPLEX=std::complex<double> -I/home/s/Download/SparseLib++/1.7/include -I/home/s/Download/SparseLib++/1.7/src -I/home/s/Download/SparseLib++/1.7/mv/include -I/home/s/Download/SparseLib++/1.7/mv/src -O0 -g3 -p -Wall -c -fmessage-length=0 -v -MMD -MP -MF"src/sparseCpp.d" -MT"src/sparseCpp.d" -o"src/sparseCpp.o" "../src/sparseCpp.cpp"
make: *** [src/sparseCpp.o] Error 1
make: Target `all' not remade because of errors.

There could be something I need to set up in Eclipse before compiling. I also checked using the 'which sh' command in Linux and get '/bin/sh' although I am not quite sure what is missing. Please help.

I am using KDevelop and I got the same error (/bin/sh: double: No such file or directory). I added this to the top of your code instead:

#define COMPLEX std::complex<double>

And it compiled and ran fine. It must be something wrong that we are doing with the -D syntax.

Good luck,

Dave

As always with programs when you have a problem with your command line arguments put them in quotes -D"COMPLEX=std::complex<double>" I imagine that the command line interpreter is < as the input piping operator.

Hi,

I have done as per your suggestions.
In both cases, I get the following error.

**** Build of configuration Debug for project sparseCpp ****

make -k all 
Building file: ../src/sparseCpp.cpp
Invoking: GCC C++ Compiler
g++ -D'COMPLEX std::complex<double>' -I/home/s/Download/SparseLib++/1.7/include -I/home/s/Download/SparseLib++/1.7/src -I/home/s/Download/SparseLib++/1.7/mv/include -I/home/s/Download/SparseLib++/1.7/mv/src -O0 -g3 -p -Wall -c -fmessage-length=0 -MMD -MP -MF"src/sparseCpp.d" -MT"src/sparseCpp.d" -o"src/sparseCpp.o" "../src/sparseCpp.cpp"
In file included from /home/s/Download/SparseLib++/1.7/mv/include/mvv.h:45,
                 from /home/s/Download/SparseLib++/1.7/include/icpre_double.h:36,
                 from ../src/sparseCpp.cpp:16:
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:56: error: expected unqualified-id before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:68: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:71: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:72: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:72: error: 'MV_Vector_COMPLEX::MV_Vector_COMPLEX(std::complex<double>)' cannot be overloaded
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:71: error: with 'MV_Vector_COMPLEX::MV_Vector_COMPLEX(std::complex<double>)'
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:82: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:82: error: 'MV_Vector_COMPLEX::MV_Vector_COMPLEX(std::complex<double>)' cannot be overloaded
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:71: error: with 'MV_Vector_COMPLEX::MV_Vector_COMPLEX(std::complex<double>)'
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:95: error: expected unqualified-id before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:102: error: expected unqualified-id before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:110: error: expected unqualified-id before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:117: error: expected unqualified-id before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:144: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h: In constructor 'MV_Vector_COMPLEX::MV_Vector_COMPLEX(std::complex<double>)':
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:83: error: class 'MV_Vector_COMPLEX' does not have any field named 'p_'
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:83: error: 'd' was not declared in this scope
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:83: error: 'N' was not declared in this scope
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:83: error: 'i' was not declared in this scope
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h: In constructor 'MV_Vector_COMPLEX::MV_Vector_COMPLEX(const MV_Vector_COMPLEX&, MV_Vector_::ref_type)':
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:86: error: class 'MV_Vector_COMPLEX' does not have any field named 'p_'
/home/s/Download/SparseLib++/1.7/mv/include/mvvc.h:86: error: 'const class MV_Vector_COMPLEX' has no member named 'p_'
In file included from /home/s/Download/SparseLib++/1.7/mv/include/mvv.h:46,
                 from /home/s/Download/SparseLib++/1.7/include/icpre_double.h:36,
                 from ../src/sparseCpp.cpp:16:
/home/s/Download/SparseLib++/1.7/mv/include/mvblasc.h: At global scope:
/home/s/Download/SparseLib++/1.7/mv/include/mvblasc.h:29: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvblasc.h:30: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvblasc.h:31: error: expected ',' or '...' before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvblasc.h:39: error: expected unqualified-id before numeric constant
/home/s/Download/SparseLib++/1.7/mv/include/mvblasc.h:40: error: expected unqualified-id before numeric constant
make: *** [src/sparseCpp.o] Error 1
make: Target `all' not remade because of errors.

Both mvvc.h and mvblasc.h are meant for the COMPLEX data type. I do not understand why these errors are thrown. Please help.

I just placed

#define COMPLEX std::complex<double>

as the very first line in the code and now I get these errors.

make -k all 
Building file: ../src/sparseCpp.cpp
Invoking: GCC C++ Compiler
g++ -I/home/s/Download/SparseLib++/1.7/include -I/home/s/Download/SparseLib++/1.7/src -I/home/s/Download/SparseLib++/1.7/mv/include -I/home/s/Download/SparseLib++/1.7/mv/src -O0 -g3 -p -Wall -c -fmessage-length=0 -MMD -MP -MF"src/sparseCpp.d" -MT"src/sparseCpp.d" -o"src/sparseCpp.o" "../src/sparseCpp.cpp"
Finished building: ../src/sparseCpp.cpp
 
Building target: sparseCpp
Invoking: GCC C++ Linker
g++  -o"sparseCpp"  ./src/sparseCpp.o   
./src/sparseCpp.o: In function `main':
/home/s/workspace/sparseCpp/Debug/../src/sparseCpp.cpp:46: undefined reference to `Coord_Mat_double::Coord_Mat_double(int, int, int, double*, int*, int*, int)'
./src/sparseCpp.o: In function `~Coord_Mat_double':
/home/s/Download/SparseLib++/1.7/include/coord_double.h:66: undefined reference to `MV_Vector_int::~MV_Vector_int()'
/home/s/Download/SparseLib++/1.7/include/coord_double.h:66: undefined reference to `MV_Vector_int::~MV_Vector_int()'
/home/s/Download/SparseLib++/1.7/include/coord_double.h:66: undefined reference to `MV_Vector_int::~MV_Vector_int()'
/home/s/Download/SparseLib++/1.7/include/coord_double.h:66: undefined reference to `MV_Vector_double::~MV_Vector_double()'
/home/s/Download/SparseLib++/1.7/include/coord_double.h:66: undefined reference to `MV_Vector_double::~MV_Vector_double()'
collect2: ld returned 1 exit status
make: *** [sparseCpp] Error 1

What is the difference in the placement of this COMPLEX preprocessor directive between this

#define COMPLEX std::complex<double>

#include <iostream>
#include <cstdlib>
#include "icpre_double.h"
#include "coord_double.h"
#include "comprow_double.h"

using namespace std;

and this ?

#include <iostream>
#include <cstdlib>
#include "icpre_double.h"
#include "coord_double.h"
#include "comprow_double.h"

#define COMPLEX std::complex<double>

using namespace std;

. The latter was the one that gave me all the errors in my previous post.

If those headers contain a definition or use of the symbol COMPLEX by placing it before you include the headers you change the headers and by placing it after them you don't.

BTW compiler/linker errors without the lines of code the correspond to are nearly (not quite but nearly) useless.

In the last listing it looks like you are missing a library or object file when you are linking.

Yes you are right. I get that explanation now.

I have not changed the code since the initial post here but will repeat it once again for clarity.

#define COMPLEX std::complex<double>
#include <iostream>
#include <cstdlib>
#include "comprow_double.h"

using namespace std;

int main() {
	cout << "Sparse example" << endl; // prints Sparse example
	
	double val[12]={1,2,3,4,5,6,7,8,9,10,11,12};
	int colind[12]={0,1,4,0,1,2,1,2,4,3,0,4};
	int rowptr[6]={0,3,6,9,10,12};
	
	Coord_Mat_double R(5,5,12,val,rowptr,colind); //----> here is where the error is signalled
	
	return 0;
}

I have checked line 66 in coord_double.h. It is the destructor. I am pasting those lines too here.

#ifndef Coord_Mat_double_H
#define Coord_Mat_double_H

#include "vecdefs.h"
#include VECTOR_H

class CompCol_Mat_double;
class CompRow_Mat_double;

class Coord_Mat_double {

private:
       VECTOR_double     val_;       // data values (nz_ elements)
       VECTOR_int    rowind_;    // row_ind (nz_ elements)
       VECTOR_int    colind_;    // col_ind (nz_ elements)

       int base_;                 // index base:  not used....
       int nz_;                   // number of nonzeros
       int dim_[2];               // number of rows, cols

public:
       Coord_Mat_double(void);
       Coord_Mat_double(const Coord_Mat_double &S);
       Coord_Mat_double(int M, int N, int nz, double *val, int *r, 
                             int *c, int base=0);
       Coord_Mat_double(const CompCol_Mat_double &C);
       Coord_Mat_double(const CompRow_Mat_double &R);
      ~Coord_Mat_double() {};

/*******************************/
/*  Access and info functions  */
/*******************************/
...........
............

I also searched the header files for where MV_Vector_double is defined. It is present in mvv.h. Must I look if the other headers also make use of this one? This is a widely-used library so I am doubtful if there is any mistake in the library but with what or how I am using it.

Sorry I was getting a little confused.

So you have the undefined reference errors?

I downloaded SparseLib and examined a couple of them

coord_double.h:66: undefined reference to `MV_Vector_int::~MV_Vector_int()'
coord_double.h:66: undefined reference to `MV_Vector_double::~MV_Vector_double()'

Those functions, the destructors on those classes, do not exist. They are defined in the right place but while all the other methods of those classes are also declared in the headers those ones aren't.

I think you are probably going to have to go through and edit the files to implement the missing functions to get this to link.

Either that or find a place that provides specific help on this library.

Is your project set up to link to all 3 libraries that build with sparselib?

Thank you so much for downloading Sparselib and having a look. I did not understand what you meant by

'Those functions, the destructors on those classes, do not exist. They are defined in the right place but while all the other methods of those classes are also declared in the headers those ones aren't.'

. Are not these mentioned in mvvd.h and mvvi.h? I see the destructor there or what is it that is wrong? I added

#include "mvv.h"

in the program but I still get the same error.

To daviddoria's question - Please let me know what the 3 libraries are you were mentioning? I have downloaded Sparselib++ from here http://math.nist.gov/sparselib/. Apart from this I did not downloaded anything else. They also mention that MV++ is shipped along with this so I did not download that. All the code for MV++ is present in Sparselib++.

Thank you indeed for looking into this problem. I am quite new to C++ and Eclipse and therefore when an error occurs I do not know if it is due to Eclipse or C++. Any and every help is valid.

Thank you so much for downloading Sparselib and having a look. I did not understand what you meant by .

You have not lost much by not understanding because I was wrong :D

I hadn't noticed that they were using .cc files and my IDE grep was set to only search .h and .cpp

Anyway what davidora is saying (and I think thay are on the right track) is that when you call the build using the makefile SparseLib++\1.7\makefile the result should be that these 3 libraries

libmv.a
libsparse.a
libspblas.a

are created in SparseLib++\1.7\lib

If when you link your application you leave these libraries out (off the linker command line) then you will get unresolved externals similar to what you have got.

The header is NOT the library, the header is just the interface to the library that you compile against. To use the library you also have to link against the binary lib file.

I downloaded it and built it. This produced 3 ".a" files (static libraries). I had to link the program to these libraries so that the symbols were defined. This is done manually with

g++ -l[library1] -l[library2]

(ensuring the library path is either on your LD_LIBRARY_PATH or you tell g++ with -L)

In Eclipse, surely you can set libraries to link to without needing this syntax.

Dave

In Eclipse, surely you can set libraries to link to without needing this syntax.

Well yes but it does rather depend on how you have your projects set up in the first place.

Personally I think Eclipse is a bit heavy weight and confusing for a new user and I particularly dislike the way it seems to think it is a separate file system independent of the actual file system.


You might want to try something a little lighter and easier like CodeBlocks

Eclipse is tough :(
I am not sure if I have done the project setup right in the first place. I certainly have not done anything similar to linking the '.a' files using Eclipse.
If I understand you right, these '.a' files are got after a successful build and then you can link/run the program. In my case, I use the 'Project Build' option in Eclipse and that is where the 'unresolved references' occur. Therefore I do not get the '.a' files. Or did you ask me to give the '-l' even before I 'build' the program? (very confusing :'( )

I need to check these corresponding '-l' settings on Eclipse before I email anything further. Tomorrow I shall get some essential things done aka groceries, laundry and room-cleaning. I shall get back on Sunday. Thank you once again. :)

I recommend you do some googling for "static libraries c++" and "c++ linking". Then, I recommend you build this program manually (without eclipse) using g++ and the -L and -l flags. THEN once that works, the only problem is doing it in the "language"/framework of Eclipse.

Good luck,

Dave

Hi,

The 3 static c++ libraries are now present in Sparselib++/1.7/lib.
I followed the email link (http://dev.eclipse.org/newslists/news.eclipse.tools.cdt/msg09156.html) to place -l and -L options in eclipse.
There still seems to be unresolved errors like this:

make -k all 
Building target: sparseCpp
Invoking: GCC C++ Linker
g++ -L/home/s/Download/SparseLib++/1.7/lib -o"sparseCpp"  ./src/sparseCpp.o   -lspblas -lmv -lsparse
/home/s/Download/SparseLib++/1.7/lib/libsparse.a(coord_double.o): In function `Coord_Mat_double::trans_mult(MV_Vector_double const&) const':
/home/s/Download/SparseLib++/1.7/src/coord_double.cc:307: undefined reference to `dcoomm_'
/home/s/Download/SparseLib++/1.7/lib/libsparse.a(coord_double.o): In function `Coord_Mat_double::operator*(MV_Vector_double const&) const':
/home/s/Download/SparseLib++/1.7/src/coord_double.cc:272: undefined reference to `dcoomm_'
collect2: ld returned 1 exit status
make: *** [sparseCpp] Error 1
make: Target `all' not remade because of errors.

I did a grep for 'dcoomm' and it is present in libsparse.a and lispblas.a. So does it look like the linking of these '.a' files is still not right ?

No it's there because they try to call them. Generally when grepping if you have the source it is better to grep the source code no the binary library. If you did you would find that the source code attempts to call these functions but they are not defined anywhere.

And that is what "undefined reference to" means, a symbol (class name, function name, variable name) was used by a piece of source code which compiled fine because the symbol was declared, however the symbol was not defined so the linker can not resolve the reference to it.

A quick Google (or your alternative other search engine) on dcoomm will show that it is part of the Sun Performance Library which appears to be a library that Sun distributed with there compiler toolset.

I couldn't actually find a source for the library but on the other hand I did stop looking once I found out what it was.

In the makefile.def that was provided in Sparselib++, the LDFLAGS mention

# g++ v. 2.7.0
#
CCC 			= g++
CC 				= gcc	
CCCFLAGS 	=  -DMV_VECTOR_BOUNDS_CHECK -g -Wall -pedantic\ 
     '-DCOMPLEX=std::complex<double>'  
CCCFLAGS 	=  -g -Wall -pedantic -O3 '-DCOMPLEX=std::complex<double>'  
LDFLAGS	= $(SPARSELIB_DIR)/lib/libsparse.a $(SPARSELIB_DIR)/lib/libspblas.a \
					$(SPARSELIB_DIR)/lib/libmv.a -lm

So I placed the exact paths to the 3 static libraries at Project->Properties->Settings->C++ Linker ->Miscellaneous->Other objects while retaining -l and -L options in my previous post. I also added an 'm' in the -l option. Now the code compiles alright :) Thank you very much.

I am not sure why we need to retain the 3 static libraries in the -l option if we are setting the path in (....->Other objects) since if I remove them from -l, the same error comes in.

-L (the path) tells it WHERE to look. -l (the libraries) tells it WHAT to look for.

Yes that is right. For now things look good :)
Thank you once again..

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.