首页 > 系统相关 >Linux下Qt创建共享库与链接共享库详解

Linux下Qt创建共享库与链接共享库详解

时间:2023-06-09 11:05:44浏览次数:42  
标签:Widget Qt int ui Linux 共享 include

随着程序写的逐渐变多,或多或少的我们都会使用别人写好的库;或者我们不想让别人看到我们的一些核心程序,可以将核心程序封装成库。本次和大家分享的是在Ubuntu下使用Qt生成共享库以及在Qt中链接共享库的方法。

 

共享库是在Linux下的称呼,在Windows下被称为动态库。这块大家需要了解的是程序在编译时使用的库和程序在运行时使用的库需要一致,不然程序可能会闪退。而且运行时库的路径如果没有设置,那么系统就会在默认的路径下进行搜索,如果没找到程序直接就挂了。之后的文章会进行总结说明的。

 

程序平台: Ubuntu14.04、 Qt5.5.1

一、Qt 创建共享库

 

  1. 创建类型为库的Qt工程

① 新建工程-> Library -> C++ 库:

Linux下Qt创建共享库与链接共享库详解_#include

 

 

②类型选择默认的共享库,填写名称并选择工程路径。简单说下库的类型分别是动态库、静态库和Qt的插件

Linux下Qt创建共享库与链接共享库详解_Qt_02

③选择默认的套件即可

④选择所需模块,这里我没有勾选任何模块

Linux下Qt创建共享库与链接共享库详解_#include_03

 

⑤设置类的基本信息

⑥完成向导

2.工程文件

①工程创建完成后,删掉了Qt生成的一些文件,文件目录如下

 

Linux下Qt创建共享库与链接共享库详解_Qt_04

 

② .pro 文件的修改,添加版本号的设置

 

QT -= core gui
 
TARGET = TestLib
TEMPLATE = lib
VERSION += 1.1.0
 
CONFIG += debug_and_release
CONFIG(debug, debug|release) {
unix: TARGET = $$join(TARGET,,,_debug)
else: TARGET = $$join(TARGET,,,d)
}
 
DEFINES += TESTLIB_LIBRARY
 
SOURCES += addlib.cpp
 
HEADERS += addlib.h
 
unix {
target.path = /usr/lib
INSTALLS += target
}

TARGET : 库的名称

TEMPLATE :模板类型,类型为lib ,即生成的是一个库文件

VERSION(新增部分) :库的版本号设置

CONFIG (新增部分) :控制编译的Debug与Release库的版本名称

 

 

3.生成共享库

该共享库实现了计算两个整型数和的功能,过于简单,莫要介意~

 

①.h文件内容

#ifndef ADDLIB_H
#define ADDLIB_H
 
class AddLib
{
public:
AddLib();
 
int myAdd(int x, int y);
};
 
#endif // ADDLIB_H

②.cpp内容

#include "addlib.h"
 
AddLib::AddLib()
{
}
 
int AddLib::myAdd(int x, int y)
{
return x + y;
}

③构建与运行

只构建的话就会直接生成共享库,如果运行的话就是下面这个样子。

Linux下Qt创建共享库与链接共享库详解_Qt_05

 

④生成动态库效果

到这里我们就已经生成好了动态库,可以看下我们添加的动态库的版本号。

注意,我这里没有区分Debug与Release版本。

Linux下Qt创建共享库与链接共享库详解_#include_06

 

 

二、链接动态库

  1. 创建工程添加文件

创建一个继承QWidget的应用程序后,在与.pro文件同级目录下添加一个如下目录组织的文件:

main.cpp

***.pro

Lib/

test/

linux_x32/

Include/

addlib.h

lib/

libTestLib.so**

 

2.借助Qt添加库

①右键项目->添加库

Linux下Qt创建共享库与链接共享库详解_#include_07

 

 

②选择链接库的类型,选择【外部库】

Linux下Qt创建共享库与链接共享库详解_共享库_08

 

 

③选择链接库的路径与平台等信息

Linux下Qt创建共享库与链接共享库详解_Qt_09

 

①.pro中新增文件

 

unix:!macx: LIBS += -L$$PWD/Lib/test/linux_x32/lib/ -lTestLib

INCLUDEPATH += $$PWD/Lib/test/linux_x32/include

DEPENDPATH += $$PWD/Lib/test/linux_x32/include

 

$$PWD :用于指定包含.pro文件目录的完整路径

INCLUDEPATH :指定了编译项目时被搜索到的 #include 目录

LIBS :指定了链接到项目中库的列表

 

④修改后的.pro文件

实际项目中我们的库可能会用到多个平台,所以一般创建如下

unix{
contains(QT_ARCH, i386){
 
INCLUDEPATH += $$PWD/Lib/test/linux_x32/include
LIBS += -L$$PWD/Lib/test/linux_x32/lib -lTestLib
}
contains(QT_ARCH, x86_64){
}
}else{
contains(QT_ARCH, i386){
}
contains(QT_ARCH, x86_64){
#64bit
}
}

3.测试程序的编写

①.h

#ifndef WIDGET_H
#define WIDGET_H
 
#include <QWidget>
 
#include "addlib.h"
 
namespace Ui {
class Widget;
}
 
class Widget : public QWidget
{
Q_OBJECT

 

public:
explicit Widget(QWidget *parent = 0);
~Widget();
 
private slots:
void on_pbn_testAddLib_clicked();
 
private:
Ui::Widget *ui;
 
AddLib m_addLib;
};
 
#endif // WIDGET_H

 

② .cpp

#include "widget.h"
#include "ui_widget.h"
#include <QDebug>
 
Widget::Widget(QWidget *parent) :
QWidget(parent),
ui(new Ui::Widget)
{
ui->setupUi(this);
}
 
Widget::~Widget()
{
delete ui;
}
 
void Widget::on_pbn_testAddLib_clicked()
{
int x = ui->le_x->text().toInt();
int y = ui->le_y->text().toInt();
 
int ret = m_addLib.myAdd(x,y);
 
ui->le_ret->setText(QString::number(ret));
 
qDebug() << "add ret is :" << ret;
}

 

③ UI输入两个数字,点击按钮后通过共享库计算,如下:

Linux下Qt创建共享库与链接共享库详解_Qt_10

 

三、后记总结

  1. 使用共享库问题与解决方法

以前在使用共享时,报了一个这样的错误:

error while loading shared libraries: libTestLib.so.1: cannot open shared object file: No such file or directory

加载共享库时失败,没找到。那会儿的解决办法是把共享库拷贝到 usr/local/lib下,这样问题就没有了,拷贝后要使用ldconfig命令。

上面的错误是在运行时没有找到共享库,在Linux下,可以使用 ldd命令查看一个可执行程序所需的库,效果如下:

 

Linux下Qt创建共享库与链接共享库详解_#include_11

 

2.为什么在Qt中运行没有报上面的错误?

由于以前使用共享库遇到过上面的问题,但是在刚刚测试共享库的时候,为什么没有报错呢?是Qt将生成的共享库放到Linux默认的搜索路径下了么?

于是我使用了locate +库名 命令进行搜索,但是并没有在其他路径下发现刚刚生成的共享库;于是我又去找配置Linux环境变量的文件,发现也没有。root下,在/etc/ld.so.conf.d文件下查看。

然鹅我并没有放弃,于是借助谷歌,搜索了下相关问题【Qt 编译工程的过程】,虽然没有找到答案,但是发现了一些线索:

Linux下Qt创建共享库与链接共享库详解_共享库_12

 

 

在Projects中的Run Environment 下的LD_LIBRARY_PATH对应的Value里面,我看到了在程序中链接库的目录。至此,我觉得我找到了原因。

3.小结中的小结

通过对一个问题的求解,我们顺藤摸瓜的会学习到很多其他知识。像本次就知道几个Linux命令的使用场景。

 

欢迎大家关注公众号 : Pou光明

 

如需工程源码可在后台留下邮箱或其他联系方式



标签:Widget,Qt,int,ui,Linux,共享,include
From: https://blog.51cto.com/u_4018548/6445811

相关文章

  • qt work
    autofolder1="./.mm";QDir*folder=newQDir;boolexist=folder->exists(folder1);if(exist){QMessageBox::warning(this,tr("createDir"),tr("Dirisalreadyexisted!"));}......
  • linux脚本书写笔记
    6月9日,记录init.d的S40network解析判断是否存在某文件: 此语句为判断目录/var/run是否存在(!-e/var/run),如果不存在则创建该目录(mkdir-p/var/run)。其中,!-e是一个逻辑运算符,用于判断文件或目录是否存在,而mkdir命令的-p选项表示如果需要的话,也会创建所有必要的父级目录。......
  • Linux安装Redis
    1、系统环境[root@localhost~]#cat/etc/redhat-release2、安装依赖yum -y installgccgcc-c++pcrepcre-develzlibzlib-developensslopenssl-devel3将redis-3.2.1.tar.gz安装包上传到服务器的/usr/local/目录下3.1解压redis压缩包[root@localhostlocal]#tar-xvfre......
  • Linux Shell 脚本创建日期文件夹
    mk-time-dir.sh#!/bin/bashdir_name=$(date'+%Y%m%d%H%M')mkdir$dir_nameecho"已创建文件夹${dir_name}"#已创建文件夹202306090936参考:Linuxdate命令......
  • Linux dlopen系列函数
    Linux提供了一套API来动态装载库,编译时候要加入-ldl(指定dl库) dlopen()函数函数定义#include<dlfcn.h>void*dlopen(constchar*filename,intflag);描述dlopen()用于加载以\0结尾的字符串文件名命名的动态共享对象(或叫动态链接库),返回一个不透明的句柄,此句柄......
  • Linux 通过修改 grub 文件禁用节能模式
    1、执行vi/etc/default/grub命令以编辑该文件 将光标移至GRUB_CMDLINE_LINUX行,在rhgb前新增intel_idle.max_cstate=0intel_pstate=disable字段,输入wq命令,按回车即能保存退出。2、生成启动文件 3、将改动写入镜像 最后执行reboot或者shutdown-rnow命令来......
  • Linux系统中GDB调试详细操作方法
    第一:启动在shell下敲gdb命令即可启动gdb,启动后会显示下述信息,出现gdb提示符。添加编译指令:gcc-ga.c-otest打开指令:gdbtest  或者gdb  然后输入:filetest➜examplegdbGNUgdb(Ubuntu8.1.1-0ubuntu1)8.1.1Copyright(C)2018F......
  • linux相关杂记
    find-namename,-inamename:文件名称符合name的文件。iname会忽略大小写find/etc-nameinit(精准查找)find/etc-name*init*(模糊查找,*任何字符)find/etc-nameinit???(模糊查找,?表示单个字符)find/etc-inameinit???(iname不区分大小写)-sizen:......
  • 《循序渐进学运维》第一阶段Linux基础
    前言循序渐进学运维系列,第一阶段的内容已经全部更新完毕。包含学习方法篇,和基础入门课程。所有内容均在csdn存档。想要学习的可以按照这个步骤进行学习,有不完善的地方欢迎在留言区留言,一起交流。第一阶段linux基础学习方法篇Linux运维学习方法篇90后,零基础学习运维,算晚吗?内含书......
  • 【linux】在阿里云服务器上部署网站 WeCenter
    文章目录前言操作环境及以有的架构上传WeCenter软件包解压并传至根目录安装weCenter1.进入阿里云后台,选择域名解析二级域名bbs.zmkjedu.com3.设置apache的配置文件4.开始安装5.全部通过后,点击下一步:6.添加管理员7.安装成功,访问首页总结前言本次实验是在现有网站www.zmkjedu.......