Qt使用技巧--定义Private类

如果查看Qt的源码,会发现很多类都会有一个***Private类。这是Qt用于封装私有操作的一种设计模式。

给出一个继承自QObject的Private类具体的实现:

MyClass.h

#include "QObject"

class MyClassPrivate;
class MyClass: public QObject{
Q_OBJECT
public:
    MyClass();
    ~MyClass();
    void foo();
    void foo2();
private:
    Q_DECLARE_PRIVATE(MyClass)
    Q_DISABLE_COPY(MyClass)
    MyClassPrivate * const d_ptr;
};

MyClassPrivate.h :注意这里继承自QObject

class MyClassPrivate: public QObject{
    Q_OBJECT
    Q_DECLARE_PUBLIC(MyClass)
public:
      MyClassPrivate(MyClass*parent) ;
      ~MyClassPrivate() ;
      void bar();
      void bar2();
private:
    MyClass *  const  q_ptr;
};

MyClass.cpp --注意这种形式Private类实现写在了MyClass.cpp中


#include "MyClass.h"
#include "QDebug"
#include "MyClassPrivate.h"
MyClassPrivate::MyClassPrivate(MyClass*parent): q_ptr(parent) {
    qDebug()<<"-------init MyClassPrivate---------";
}

MyClassPrivate::~MyClassPrivate() {

}

void MyClassPrivate::bar() {
    qDebug()<<"--------MyClassPrivate::bar--------";
}

void MyClassPrivate::bar2() {
    Q_Q(MyClass);
    qDebug()<<"--------MyClassPrivate::bar2--------";
    q->foo2();
}

MyClass::MyClass(): d_ptr(new MyClassPrivate(this)) {
    qDebug()<<"--------init MyClass--------";
}

MyClass::~MyClass() {
    delete d_ptr;
}

void MyClass::foo() {
    qDebug()<<"--------MyClass::foo--------";
    Q_D(MyClass);
    d->bar();
    d->bar2();
}

void MyClass::foo2() {
    qDebug()<<"--------MyClass::foo2--------";
}

main.cpp

#include 
#include 
#include "MyClass.h"

int main(int argc, char *argv[]) {
    QCoreApplication a(argc, argv);
    qDebug() << "Hello World";
    MyClass pub;
    pub.foo();
    return QCoreApplication::exec();
}

对应CMake目录有两种结构,在CMakeList实现上 针对这两种结构有一点区别

首先是第一种结构:

 Qt使用技巧--定义Private类_第1张图片

cmake_minimum_required(VERSION 3.23)
project(MyClass)

set(CMAKE_CXX_STANDARD 14)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)
set(CMAKE_AUTOUIC ON)
#set(CMAKE_PREFIX_PATH C:\\Qt\\Qt5.15.2\\5.15.2\\msvc2019_64)
include_directories(include )

file(GLOB_RECURSE  DIR_INC_PUB include/*.h) #Qt使用的时候
aux_source_directory(src DIR_SRC)

find_package(Qt5 COMPONENTS
        Core
        REQUIRED)

add_executable(MyClass ${DIR_SRC}  ${DIR_INC_PUB}  )
target_link_libraries(MyClass
        Qt5::Core
        ) 

 这种结构中规中矩,会把Private类暴露给客户

第二种结构:Private对客户隐藏,不对外暴露在include文件夹里

Qt使用技巧--定义Private类_第2张图片

 这种时候不修改Cmake编译不通过

一种解决方案是去掉Private类里的Q_OBJECT宏,这时可以编译通过Qt使用技巧--定义Private类_第3张图片

 另一种是修改CMake

file(GLOB_RECURSE  DIR_INC_PRIVATE src/*.h)
add_executable(MyClass ${DIR_SRC}  ${DIR_INC_PUB} ${DIR_INC_PRIVATE})

原因是Private类的Q_OBJECT在编译期间moc展开未被正确连接。 

当然,也可以把Private类的实现单独写在***Private.cpp,这个时候就不会有编译问题。

Qt使用技巧--定义Private类_第4张图片

 但这样的结构上就稍微不如之前的形式了。

你可能感兴趣的:(Qt技巧总结,qt,开发语言,c++)