Using the QJson library - c++

I know it's a stupid question, but still.
I want to use the QJson library in my project. I've downloaded the tarball from the official site (probably need to mention that I'm under 64-bit Ubuntu 12.04). The INSTALL file has the following instructions
mkdir build
cd build
cmake -DCMAKE_INSTALL_PREFIX=_preferred_path_ ..
make
make install
/sbin/ldconfig, if necessary
which I followed precisely. I've got the /include, /lib and share folders of QJson added to my /usr/local.
After that, I open my IDE (which is QtCreator), and make a test project with the following simple code:
#include <QVariant>
#include <qjson/serializer.h>
int main(int argc, char *argv[])
{
QJson::Serializer s;
QVariantMap map;
map["hello"] = QVariantList() <<"t1"<<"t2";
QByteArray json = s.serialize(map);
}
The #include is handled fine, all the types are recognized, the auto-complete for the QJson classes works fine. However, when trying to compile, I'm getting this (full path removed for readability):
<...>/QJsonTest/main.cpp:15: undefined reference to `QJson::Serializer::Serializer()'
<...>/QJsonTest/main.cpp:18: undefined reference to `QJson::Serializer::serialize(QVariant const&)'
<...>/QJsonTest/main.cpp:18: undefined reference to `QJson::Serializer::~Serializer()'
<...>/QJsonTest/main.cpp:18: undefined reference to `QJson::Serializer::~Serializer()'
collect2: ld returned 1 exit status
What's the reason, and how do I make it work?

You are hitting linker (not compiler) errors. You need to add the path to your QJson library files with a -L option

Related

Compiling boost::asio example on Windows

I am trying to switch to Windows environment from Linux, but find it a very hard path.
This time I wanted to test if I can work with boost library.
I had problems with compiling boost on windows, so I downloaded precompiled version. I unpacked everything and tested positively that I can compile the header-only librariers.
Then I copied some simple boost::asio example. I set up everything in Eclipse. Compilation went fine, but during linking I got 'undefined reference' problem to 'boost::system' internal stuff.
C:/Users/jacek/cpp/boost_1_62_0/boost/system/error_code.hpp:221: undefined reference to `boost::system::generic_category()'
C:/Users/jacek/cpp/boost_1_62_0/boost/system/error_code.hpp:222: undefined reference to `boost::system::generic_category()'
C:/Users/jacek/cpp/boost_1_62_0/boost/system/error_code.hpp:223: undefined reference to `boost::system::system_category()'
So I added '-lboost_system', as well as the path to the libraries directory, to my linking options. But this did not help.
g++ "-LC:\\Users\\jacek\\cpp\\boost_1_62_0\\lib64-msvc-14.0" -o TestAsio.exe "src\\Main.o" -lboost_system
I checked the libraries directory and found there is a bunch of files containing 'boost_system' in the name. They are:
libboost_system-vc140-mt-1_62.lib
libboost_system-vc140-mt-gd-1_62.lib
libboost_system-vc140-mt-s-1_62.lib
libboost_system-vc140-mt-sgd-1_62.lib
libboost_system-vc140-s-1_62.lib
libboost_system-vc140-sgd-1_62.lib
I did not know which I should use. I tried adding 'libboost_system-vc140-mt-1_62' to the linking options, I tried all other files, I tried renaming the files to the linux pattern 'libboost_system.a', but nothing worked.
g++ "-LC:\\Users\\jacek\\cpp\\boost_1_62_0\\lib64-msvc-14.0" -o TestAsio.exe "src\\Main.o" -llibboost_system-vc140-mt-1_62 -llibboost_system-vc140-mt-gd-1_62 -llibboost_system-vc140-mt-s-1_62 -llibboost_system-vc140-mt-sgd-1_62 -llibboost_system-vc140-s-1_62 -llibboost_system-vc140-sgd-1_62
What am I doing wrong here?
Please help...
YotKay
I solved it myself with the help of a comment from this post: boost asio example compilation error
It looks like the precompiled version of Boost is created with Visual Studion and is NOT COMPATIBLE with G++. I if I decided to install MinGW then I cannot use the precompiled version of boost, but must compile it myself using g++.
I did that.
Now I have libraries compiled with G++.
I specify the path to the boost system library like that:
c:\Users\jacek\cpp\boost_1_62_0\libraries\boost\bin.v2\libs\system\build\gcc-mingw-6.2.0\debug\link-static\
and add this option:
-lboost_system-mgw62-d-1_62
Now the problem with boost::system disappears. However, another one pops up with boost asio, but luckily the answer is here: MinGW linker error: winsock
The example works fine now on my Windows 10 laptop.
#include <boost/asio/io_service.hpp>
#include <boost/asio/steady_timer.hpp>
#include <chrono>
#include <iostream>
using namespace boost::asio;
int main()
{
io_service ioservice;
steady_timer timer{ioservice, std::chrono::seconds{3}};
timer.async_wait([](const boost::system::error_code &ec)
{ std::cout << "3 sec\n"; });
ioservice.run();
}

Installing ICU libraries and compiling program

I'm exploring using IBM's ICU to work with Unicode strings, by writing sample code.
Following the steps from ICU's page, I unpacked the contents of icu4c-57_1-RHEL6-x64.tgz onto /usr/local/include and /usr/local/bin, on my Linux box. Would this suffice for one to start using the ICU library?
Sample code:
#include <iostream>
#include <string.h>
#include <locale.h>
#include "unicode/coll.h"
#include "unicode/utypes.h"
using namespace icu;
using namespace std;
int main()
{
UErrorCode success = U_ZERO_ERROR;
Collator *collator = Collator::createInstance(success);
collator->setStrength(Collator::PRIMARY);
if (collator->compare("débárquér", "debarquer") == 0) {
cout << "Strings are equal" << endl;
} else {
cout << "Strings are unequal" << endl;
}
return 0;
}
Compilation of this code fails:
$ g++ unicode.cc
/tmp/ccUknunM.o: In function `main':
unicode.cc:(.text+0x20): undefined reference to `icu_4_2::Collator::createInstance(UErrorCode&)'
unicode.cc:(.text+0x61): undefined reference to `icu_4_2::UnicodeString::UnicodeString(char const*)'
unicode.cc:(.text+0x72): undefined reference to `icu_4_2::UnicodeString::UnicodeString(char const*)'
unicode.cc:(.text+0x97): undefined reference to `icu_4_2::UnicodeString::~UnicodeString()'
unicode.cc:(.text+0xaa): undefined reference to `icu_4_2::UnicodeString::~UnicodeString()'
unicode.cc:(.text+0xc3): undefined reference to `icu_4_2::UnicodeString::~UnicodeString()'
unicode.cc:(.text+0xdd): undefined reference to `icu_4_2::UnicodeString::~UnicodeString()'
collect2: ld returned 1 exit status
From the output, it appears that ICU installation is either incorrect or incomplete. What am I missing?
Thanks!
Edit:
When I search for the file coll.h, this is what I see:
$ find /usr/local/ -name coll.h
/usr/local/bin/usr/local/include/unicode/coll.h
/usr/local/include/usr/local/include/unicode/coll.h
Does this look alright?
The "steps from the ICU page" state that...
...the .tgz file unpacks to a "/usr/local" type hierarchy.
Looking at the archive contents...
$ tar tzf icu4c-57_1-RHEL6-x64.tgz
readme.txt
usr/
usr/local/
usr/local/lib/
usr/local/lib/libicudata.so.57.1
usr/local/lib/libicudata.so
usr/local/lib/libicudata.so.57
...
...you are supposed to extract that archive to root (/), not once to /usr/local/bin and once to /usr/local/include as you did. (The path repetition in your find results should have been a hint. No, it does not look alright at all.)
That being said, what you really should have done is checking your distribution's package manager for the ICU packages (libicu, libicu-dev, ...). Installing via your package manager has several advantages:
It avoids problems like the one you just encountered.
It ensures that the version of ICU you are using for your programs is the same as used by other package's programs; ending up with a binary that links two different versions of the ICU libraries is just asking for trouble.
It keeps the package updated automatically.
Depending on your distribution, you might not get the absolute latest release, but that does usually not matter much.
Once you have a functioning installtion, third-party frameworks commonly require you to explicitly state an include/ subdirectory, either in the source or the build file, to make it clear which framework(s) you are actually using. For ICU, the prefix is (somewhat unintuitively) unicode... and they don't make this explicit in their documentation, where it reads...
#include <unistr.h>
So, if you instead write...
#include "unicode/coll.h"
...it should work.

Getting the MySQL C API working with MinGW

It's been days searching for a way to get the MySQL C API working with a MinGW compiler, and frankly I have to say this is getting very frustrating.
I'm trying to compile the minimal example:
#include <my_global.h>
#include <mysql.h>
int main(int argc, char **argv)
{
printf("MySQL client version: %s\n", mysql_get_client_info());
exit(0);
}
and I keep on getting:
[Linker Error] undefined reference to `mysql_get_client_info#0'
I have compiled the libraries (including libmysql.a which contains mysql_get_client_info) and properly linked them, included all include and lib directories properly. Basiacly, everything is done by the letter according not only to the tutorials but also to forum posts which dealt specifically with this problem.
Now, what am I doing wrong?
Thanks
Having looked at your make-file, it would appear you've forgotten the mysql flags, required for your code to compile. On linux, you'd have to include the output of mysql_config --cflags --libs in the make file.
Add those to your makefile and the code should compile just fine.

Trying to install and use LAPACK++, problems with loading shared libraries

I am new to using libraries and I am having some trouble with lapack++ and getting it to work. I will explain what I have done and tried so far.
First I installed BLAS and LAPACK and that went fine. I now have installed LAPACK++ version 2.5.2 (http://lapackpp.sourceforge.net/) so I can call various linear algebra routines in C/C++. After I configure, make and then make install it places all the C/C++ header files in /usr/local/include/lapackpp/ some of which are..
arch.h
bmd.h
gmf.h
lapackc.h
lautil.h
spdmd.h
ultgmd.h
bfd.h
...
and also the following files in /usr/local/lib
liblapackpp.la
liblapackpp.so
liblapackpp.so.14
liblapackpp.so.14.2.0
Now if I try to compile using g++ the simple code of
#include <lapackpp/lapackpp.h>
using namespace std;
int main(int argc, char** argv) {
return 0;
}
I get the following output...
In file included from /usr/local/include/lapackpp/lapackc.h:14,
from /usr/local/include/lapackpp/lapack.h:10,
from /usr/local/include/lapackpp/lapackpp.h:16,
from test.cpp:1:
/usr/local/include/lapackpp/lacomplex.h:45:23: error: laversion.h: No such file or directory
/usr/local/include/lapackpp/lacomplex.h:48:17: error: f2c.h: No such file or directory
In file included from /usr/local/include/lapackpp/lapackpp.h:47,
from test.cpp:1:
/usr/local/include/lapackpp/latmpl.h:36:22: error: lafnames.h: No such file or directory
I solved this problem by writing the location of the header file explicitly in the header file that was causing trouble.
Eg. I replaced
#include
with
#include
After doing this my code compiles fine.
Now if I try to compile the code
#include <cstdlib>
#include <iostream>
#include <lapackpp/lapackpp.h>
using namespace std;
int main(int argc, char** argv) {
LaGenMatDouble A(5,5);
cout << "This is a test." << endl;
return 0;
}
by typing
g++ test.cpp -o test -I usr/local/include/lapackpp
I get the following errors
/tmp/ccAq6nkP.o: In function `main':
test.cpp:(.text+0x22): undefined reference to `LaGenMatDouble::LaGenMatDouble(int, int)'
test.cpp:(.text+0x4f): undefined reference to `LaGenMatDouble::~LaGenMatDouble()'
test.cpp:(.text+0x67): undefined reference to `LaGenMatDouble::~LaGenMatDouble()'
collect2: ld returned 1 exit status
(Info on LaGenMatDouble is here )
which suggests I may be linking to the library wrong?
After some googling I realised that I needed to link to the header files using -I and the shared library by -L and the library itself by -llapackpp, so then I typed
g++ test.cpp -o test -I usr/local/include/lapackpp -L usr/local/lib -llapackpp
which compiled the code, now when I ran the program by typing ./test I go the error
./test: error while loading shared libraries: liblapackpp.so.14: cannot open shared object file: No such file or directory
and now I am confused.
I am unsure if this has anything to do with the problem but when I type
pkg-config lapackpp --libs
I get
Package lapackpp was not found in the pkg-config search path.
Perhaps you should add the directory containing `lapackpp.pc'
to the PKG_CONFIG_PATH environment variable
No package 'lapackpp' found
The same happens for lapack and blas too.
I am unsure what to do. Any help would be very much appreciated, thanks!
Linking goes fine because you tell to the linker where the library is, but execution failed because the loader doesn't know anything about the location of your libraries (you can check that performing ldd yourapp, which shows the library needed by your application).
Usually, you can solve that by telling to the loader where the library is through the variable LD_LIBRARY_PATH, but it is a crude tool. A different solution is to encode that instruction directly in the executable, as described here, or simply to link statically your application using the switch -static
If you're after a C++ library that wraps LAPACK (and/or BLAS), you might be better off using a more modern library such as Armadillo. Besides using LAPACK as a backend for solvers and matrix factorizations, it uses expression templates to speed up operations.

Undefined Symbol: _sf_open (Simple audio stuff on OSX)

I'm trying to get into C++ programming, and I'm quite struggling against the little details. Right now, I'm trying to get the snippet below to work, and apparently it will compile, but not link. (error message is a the bottom of this post)
I'm using libsndfile to open audio files, and the linker doesn't seem to find the corrent library files for it. This is on OS X 10.5.
I've downloaded libsndfile from mega-nerd.com and installed it via the ususal configure, make, sudo make install procedure. Is there anything else I need to do?
Edit: I have macports installed on my system, if that's of any concern.
Here's my code:
#include <iostream>
#include <string>
#include <sndfile.h>
#include "stereoSplit.h"
using namespace std;
int stereoSplit(string filename)
{
cout << filename;
SF_INFO sfinfo;
sfinfo.format = 0;
SNDFILE * soundfile;
soundfile = sf_open( filename.c_str(), SFM_READ, &sfinfo );
return 0;
}
int main (int argc, char const *argv[])
{
return stereoSplit("testStereo.wav");
}
And here's the complete error message:
Undefined symbols:
"_sf_open", referenced from:
stereoSplit(std::basic_string<char, std::char_traits<char>, std::allocator<char> >)in cc3hvkkk.o
ld: symbol(s) not found
collect2: ld returned 1 exit status
You need to link in the library. Your compiler command should look something like:
g++ mystuff.cpp -lsndfile
To link the library in Xcode, select the project target, add a new item to Link binary with libraries, and find the libsndfile.1.dynlib on your computer.