[qt5学习笔记]用vs2022(msvc2017)+copilot进行QtWidgetsApplication源码解析

一直没深入了解qt,又一段时间没写qt,重新捡起来。

开发环境

本地vs2022(msvc2017, v14.30)先升级到最新版本,方便使用copilot。
参考 VS2022+QT5环境搭建 下载 qt5.14.2

用vs的qt插件设置qt5.14.2x86路径,x64版本未安装。
创建一个默认的QtWidgetsApplication程序。

工程文件及生成关系见编译输出

1>------ 已启动全部重新生成: 项目: QtWidgetsApplication1, 配置: Debug Win32 ------
1> Qt/MSBuild: 3.3.1.1
1>Reading Qt configuration (C:/Qt/Qt5.14.2/5.14.2/msvc2017/bin/qmake)
1> Qt: 5.14.2
1>uic QtWidgetsApplication1.ui
1>rcc QtWidgetsApplication1.qrc
1>moc QtWidgetsApplication1.h
1>stdafx.cpp
1>QtWidgetsApplication1.cpp
1>main.cpp
1>qrc_QtWidgetsApplication1.cpp
1>moc_QtWidgetsApplication1.cpp
1>QtWidgetsApplication1.vcxproj -> C:\code\cpp_test\QtWidgetsApplication1\Debug\QtWidgetsApplication1.exe
========== 全部重新生成: 1 成功,0 失败,0 已跳过 ==========
========== 重新生成 于 23:35 完成,耗时 05.139==========

uic rcc moc三种自动生成的qt文件

QtWidgetsApplication1.h(有Q_OBJECT) 对应

QtWidgetsApplication1\Debug\qt\moc\moc_QtWidgetsApplication1.cpp
QtWidgetsApplication1是唯一一个界面类,头文件里面的Q_OBJECT会触发生成moc_*.cpp文件。这个moc文件需要展开说。
QtWidgetsApplication1.h关联了自动生成的ui_QtWidgetsApplication1.h文件,Ui::QtWidgetsApplication1Class类在此定义。
QtWidgetsApplication1 界面类继承QMainWindow直接获得主窗口所有技能。Q_OBJECT宏放后面展开描述。

#include <QtWidgets/QMainWindow>
#include "ui_QtWidgetsApplication1.h"class QtWidgetsApplication1 : public QMainWindow
{Q_OBJECTpublic:QtWidgetsApplication1(QWidget *parent = nullptr);~QtWidgetsApplication1();private:Ui::QtWidgetsApplication1Class ui;
};

moc_QtWidgetsApplication1.cpp代码如下:

#include "…/…/…/QtWidgetsApplication1.h"确保被前置定义了。并通过编译条件自检,存在错误时,编译期会输出错误信息。
struct qt_meta_stringdata_QtWidgetsApplication1_t 存储类名的元数据。
QT_MOC_LITERAL 宏用于初始化 QByteArrayData 结构体.

moc代码使得 Qt 的信号和槽机制能够在运行时正确工作。我觉得关键点就是利用QObject派生形成界面数据树,用各种静态函数、元数据等形成自描述信息,方便qt代码在界面树中检索信号槽。

#include <memory>
#include "stdafx.h"
#include "../../../QtWidgetsApplication1.h"
#include <QtCore/qbytearray.h>
#include <QtCore/qmetatype.h>
#if !defined(Q_MOC_OUTPUT_REVISION)
#error "The header file 'QtWidgetsApplication1.h' doesn't include <QObject>."
#elif Q_MOC_OUTPUT_REVISION != 67
#error "This file was generated using the moc from 5.14.2. It"
#error "cannot be used with the include files from this version of Qt."
#error "(The moc has changed too much.)"
#endifQT_BEGIN_MOC_NAMESPACE
QT_WARNING_PUSH
QT_WARNING_DISABLE_DEPRECATED
struct qt_meta_stringdata_QtWidgetsApplication1_t {QByteArrayData data[1];char stringdata0[22];//存储类名的元数据
};
//初始化 QByteArrayData 结构体
#define QT_MOC_LITERAL(idx, ofs, len) \Q_STATIC_BYTE_ARRAY_DATA_HEADER_INITIALIZER_WITH_OFFSET(len, \qptrdiff(offsetof(qt_meta_stringdata_QtWidgetsApplication1_t, stringdata0) + ofs \- idx * sizeof(QByteArrayData)) \)//静态常量,包含了类名 QtWidgetsApplication1 的元数据。
static const qt_meta_stringdata_QtWidgetsApplication1_t qt_meta_stringdata_QtWidgetsApplication1 = {{
QT_MOC_LITERAL(0, 0, 21) // "QtWidgetsApplication1"},"QtWidgetsApplication1"
};
#undef QT_MOC_LITERAL//静态常量数组 qt_meta_data_QtWidgetsApplication1,用于存储类的元数据。
//这个数组包含了类的修订版本、类名、类信息、方法、属性、枚举、构造函数、标志和信号的数量。
static const uint qt_meta_data_QtWidgetsApplication1[] = {// content:8,       // revision0,       // classname0,    0, // classinfo0,    0, // methods0,    0, // properties0,    0, // enums/sets0,    0, // constructors0,       // flags0,       // signalCount0        // eod
};//静态成员函数,用于处理元对象系统的调用
void QtWidgetsApplication1::qt_static_metacall(QObject *_o, QMetaObject::Call _c, int _id, void **_a)
{Q_UNUSED(_o);Q_UNUSED(_id);Q_UNUSED(_c);Q_UNUSED(_a);
}//静态常量 QMetaObject,用于存储类的元对象信息。
//它包含了父类的元对象(QMainWindow::staticMetaObject)、类名的元数据、类的元数据、静态元调用函数和其他一些指针。
QT_INIT_METAOBJECT const QMetaObject QtWidgetsApplication1::staticMetaObject = { {QMetaObject::SuperData::link<QMainWindow::staticMetaObject>(),qt_meta_stringdata_QtWidgetsApplication1.data,qt_meta_data_QtWidgetsApplication1,qt_static_metacall,nullptr,nullptr
} };//metaObject 函数返回类的元对象。
//如果对象有动态元对象,则返回动态元对象;
//否则,返回静态元对象。
const QMetaObject *QtWidgetsApplication1::metaObject() const
{return QObject::d_ptr->metaObject ? QObject::d_ptr->dynamicMetaObject() : &staticMetaObject;
}//qt_metacast 函数用于在运行时进行类型转换。
//如果传入的类名与 QtWidgetsApplication1 匹配,则返回当前对象的指针;
//否则,调用父类的 qt_metacast 函数。
void *QtWidgetsApplication1::qt_metacast(const char *_clname)
{if (!_clname) return nullptr;if (!strcmp(_clname, qt_meta_stringdata_QtWidgetsApplication1.stringdata0))return static_cast<void*>(this);return QMainWindow::qt_metacast(_clname);
}//qt_metacall 函数用于处理元对象系统的调用。
//在这个例子中,它调用父类的 qt_metacall 函数,并返回调用的 ID。
int QtWidgetsApplication1::qt_metacall(QMetaObject::Call _c, int _id, void **_a)
{_id = QMainWindow::qt_metacall(_c, _id, _a);return _id;
}
QT_WARNING_POP
QT_END_MOC_NAMESPACE

QtWidgetsApplication1.qrc 对应

QtWidgetsApplication1\Debug\qt\rcc\qrc_QtWidgetsApplication1.cpp
QtWidgetsApplication1.qrc 是一个xml片段文件,用于描述资源文件数据集,方便程序访问资源文件。

<RCC><qresource prefix="/QtWidgetsApplication1"><file>QtWidgetsApplication1.ico</file></qresource>
</RCC>

生成的主要代码如下:
关键点是当前qrc cpp编译单元中有一个全局对象struct initializer dummy;这个对象会利用cpp的构造析构函数调用全局init和cleanup函数,避免手工编码管理资源文件相关的内存。

int QT_RCC_MANGLE_NAMESPACE(qInitResources_QtWidgetsApplication1)();
int QT_RCC_MANGLE_NAMESPACE(qInitResources_QtWidgetsApplication1)()
{return 1;
}int QT_RCC_MANGLE_NAMESPACE(qCleanupResources_QtWidgetsApplication1)();
int QT_RCC_MANGLE_NAMESPACE(qCleanupResources_QtWidgetsApplication1)()
{return 1;
}namespace {struct initializer {initializer() { QT_RCC_MANGLE_NAMESPACE(qInitResources_QtWidgetsApplication1)(); }~initializer() { QT_RCC_MANGLE_NAMESPACE(qCleanupResources_QtWidgetsApplication1)(); }} dummy;
}

QtWidgetsApplication1.ui 对应

QtWidgetsApplication1\Debug\qt\uic\ui_QtWidgetsApplication1.h
QtWidgetsApplication1.ui 也是一个xml片段文件,用来描述界面,例如尺寸、内容、布局等。
需要注意的是,ui文件关联了qrc resources文件。

<UI version="4.0" ><class>QtWidgetsApplication1Class</class><widget class="QMainWindow" name="QtWidgetsApplication1Class" ><property name="objectName" ><string notr="true">QtWidgetsApplication1Class</string></property><property name="geometry" ><rect><x>0</x><y>0</y><width>600</width><height>400</height></rect></property><property name="windowTitle" ><string>QtWidgetsApplication1</string></property>  <widget class="QMenuBar" name="menuBar" /><widget class="QToolBar" name="mainToolBar" /><widget class="QWidget" name="centralWidget" /><widget class="QStatusBar" name="statusBar" /></widget><layoutDefault spacing="6" margin="11" /><pixmapfunction></pixmapfunction><resources><include location="QtWidgetsApplication1.qrc"/></resources><connections/>
</UI>

ui文件对应的ui h文件内容如下:
setupUi 方法设置用户界面
retranslateUi 方法翻译用户界面
Ui::QtWidgetsApplication1Class 类继承自 Ui_QtWidgetsApplication1Class,简化了用户代码的使用。

class Ui_QtWidgetsApplication1Class
{
public:QMenuBar *menuBar;QToolBar *mainToolBar;QWidget *centralWidget;QStatusBar *statusBar;void setupUi(QMainWindow *QtWidgetsApplication1Class){if (QtWidgetsApplication1Class->objectName().isEmpty())QtWidgetsApplication1Class->setObjectName(QString::fromUtf8("QtWidgetsApplication1Class"));QtWidgetsApplication1Class->resize(600, 400);menuBar = new QMenuBar(QtWidgetsApplication1Class);menuBar->setObjectName(QString::fromUtf8("menuBar"));QtWidgetsApplication1Class->setMenuBar(menuBar);mainToolBar = new QToolBar(QtWidgetsApplication1Class);mainToolBar->setObjectName(QString::fromUtf8("mainToolBar"));QtWidgetsApplication1Class->addToolBar(mainToolBar);centralWidget = new QWidget(QtWidgetsApplication1Class);centralWidget->setObjectName(QString::fromUtf8("centralWidget"));QtWidgetsApplication1Class->setCentralWidget(centralWidget);statusBar = new QStatusBar(QtWidgetsApplication1Class);statusBar->setObjectName(QString::fromUtf8("statusBar"));QtWidgetsApplication1Class->setStatusBar(statusBar);retranslateUi(QtWidgetsApplication1Class);QMetaObject::connectSlotsByName(QtWidgetsApplication1Class);} // setupUivoid retranslateUi(QMainWindow *QtWidgetsApplication1Class){QtWidgetsApplication1Class->setWindowTitle(QCoreApplication::translate("QtWidgetsApplication1Class", "QtWidgetsApplication1", nullptr));} // retranslateUi};namespace Ui {class QtWidgetsApplication1Class: public Ui_QtWidgetsApplication1Class {};
} // namespace Ui

编译生成的qt环境信息:

QT_SYSROOT:
QT_INSTALL_PREFIX:C:/Qt/Qt5.14.2/5.14.2/msvc2017
QT_INSTALL_ARCHDATA:C:/Qt/Qt5.14.2/5.14.2/msvc2017
QT_INSTALL_DATA:C:/Qt/Qt5.14.2/5.14.2/msvc2017
QT_INSTALL_DOCS:C:/Qt/Qt5.14.2/Docs/Qt-5.14.2
QT_INSTALL_HEADERS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/include
QT_INSTALL_LIBS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/lib
QT_INSTALL_LIBEXECS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/bin
QT_INSTALL_BINS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/bin
QT_INSTALL_TESTS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/tests
QT_INSTALL_PLUGINS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/plugins
QT_INSTALL_IMPORTS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/imports
QT_INSTALL_QML:C:/Qt/Qt5.14.2/5.14.2/msvc2017/qml
QT_INSTALL_TRANSLATIONS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/translations
QT_INSTALL_CONFIGURATION:
QT_INSTALL_EXAMPLES:C:/Qt/Qt5.14.2/Examples/Qt-5.14.2
QT_INSTALL_DEMOS:C:/Qt/Qt5.14.2/Examples/Qt-5.14.2
QT_HOST_PREFIX:C:/Qt/Qt5.14.2/5.14.2/msvc2017
QT_HOST_DATA:C:/Qt/Qt5.14.2/5.14.2/msvc2017
QT_HOST_BINS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/bin
QT_HOST_LIBS:C:/Qt/Qt5.14.2/5.14.2/msvc2017/lib
QMAKE_SPEC:win32-msvc
QMAKE_XSPEC:win32-msvc
QMAKE_VERSION:3.1
QT_VERSION:5.14.2

在stdafx.h中只有#include
默认加载的qt库:QT = core gui widgets

main.cpp

Qt 应用程序的入口点。
main之前的初始化过程由编译期生成。

#include "stdafx.h"
#include "QtWidgetsApplication1.h"
#include <QtWidgets/QApplication>int main(int argc, char *argv[])
{//QApplication 对象负责管理应用程序的控制流和主要设置。//它处理窗口系统的初始化、事件循环的启动和管理、以及应用程序级别的设置。QApplication a(argc, argv);//Qt 应用程序的基础对象//应用程序的主窗口类.调用 setupUi 方法来初始化用户界面组件QtWidgetsApplication1 w;w.show();//将窗口显示在屏幕上,并使其可见。//a.exec()启动应用程序的事件循环//事件循环会一直运行,直到调用 QApplication::quit() 或关闭所有窗口。return a.exec();
}

QApplication 对象 a 和 QtWidgetsApplication1 对象 w 之间的关联和交互主要通过以下方式实现:

  1. 事件循环管理:
    • QApplication 对象 a 负责管理整个应用程序的事件循环。所有的用户事件(如按键、鼠标点击等)都会通过 QApplication 对象传递给相应的窗口和控件。
    • 当用户与 QtWidgetsApplication1 窗口 w 进行交互时,这些事件会被 QApplication 对象捕获并分发给 w 进行处理。
  2. 窗口管理:
    • QApplication 对象 a 负责管理应用程序中的所有窗口,包括 QtWidgetsApplication1 窗口 w。它确保窗口的创建、显示和关闭都能正确处理。
    • QApplication 对象还负责处理窗口之间的焦点切换、窗口的最小化和最大化等操作。
  3. 信号和槽机制:
    • QApplication 对象 a 负责管理信号和槽的连接和分发。当某个信号被触发时,QApplication 对象会调用相应的槽函数来处理该信号。

qApp 是一个全局指针,指向当前应用程序的唯一实例 QApplication 对象。

QApplication 的构造函数会将 a 的指针存储在 QCoreApplication 的静态成员变量中,这样 QCoreApplication::instance() 就可以返回这个指针。

通过qApp 就可以遍历整个当前app进程的界面数据

通过 qApp 可以遍历整个当前应用程序的界面数据。
qApp 是一个全局指针,指向当前应用程序的唯一实例 QApplication 或 QGuiApplication 对象。
通过 qApp,你可以访问和操作应用程序的许多全局属性和方法,包括所有窗口和控件。

访问所有窗口
QGuiApplication 提供了几个静态方法,可以用来获取应用程序中的所有窗口:
• QGuiApplication::allWindows(): 返回应用程序中所有窗口的列表。
• QGuiApplication::topLevelWindows(): 返回应用程序中所有顶级窗口的列表。

访问焦点窗口和对象
• QGuiApplication::focusWindow(): 返回当前具有焦点的窗口。
• QGuiApplication::focusObject(): 返回当前具有焦点的对象。

访问屏幕信息
• QGuiApplication::primaryScreen(): 返回主屏幕对象。
• QGuiApplication::screens(): 返回所有屏幕的列表。
• QGuiApplication::screenAt(const QPoint &point): 返回指定点所在的屏幕。

用QObject构成类定义树,用qApp构成进程数据树

个人觉得,用QObject构成类定义树,用qApp构成进程数据树,这是qt的核心设计理念。
信号和槽机制 (Signals and Slots),通过信号(字符串或其它注册key)查找调用函数,实现了松耦合(解耦合)。直接调用函数属于紧耦合关系。

connect(senderObject, &SenderClass::signalName, receiverObject, &ReceiverClass::slotName);

Qt 的元对象系统支持运行时类型信息、信号和槽机制、属性系统等。QObject 类及其子类都支持元对象系统。
本质是通过moc自动生成自描述信息,挂接到qt类体系和运行时数据体系中。

Qt 是一个事件驱动的框架,所有的用户交互(如按键、鼠标点击等)都会生成事件,并通过事件循环进行处理。QApplication 对象负责管理事件循环。界面程序似乎都具备这个特性。

Qt 支持插件机制,允许开发者动态加载和使用插件。QPluginLoader 类用于加载插件,
QFactoryInterface 类用于定义插件接口。

Qt 提供了强大的国际化和本地化支持,允许开发者为应用程序提供多语言支持。QTranslator 类用于加载翻译文件,tr() 函数用于标记需要翻译的字符串。

模型-视图-控制器 (Model-View-Controller, MVC) 模式

Qt 提供了丰富的模型-视图框架,用于实现数据与用户界面之间的分离。QAbstractItemModel 是模型的基类,QListView、QTableView 等是视图的基类。然后通过信号和槽进行控制。

QStandardItemModel *model = new QStandardItemModel();
QListView *view = new QListView();
view->setModel(model);// 添加控制逻辑,例如信号和槽的连接
connect(view, &QListView::clicked, this, &QtWidgetsApplication1::onItemClicked);

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/71074.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

家里装修想用投影仪,如何选择?装修中应该注意什么?

越来越多的业主在装修的时候抛弃了传统的电视&#xff0c;采用投影仪。 和这些业主聊天&#xff0c;选用投影仪有两个目的&#xff0c;第1是把电视机拿掉&#xff0c;这样能让家里的小朋友不看电视&#xff0c;保护小朋友的眼睛。 第2是选用投影仪&#xff0c;幕布都会装的比较…

javaEE初阶————多线程初阶(4)

8.1 单例模式 这又是什么新的神奇玩意呢&#xff0c;我们先不谈单例模式&#xff0c;先来谈谈设计模式&#xff0c;什么是设计模式呢&#xff0c;我们只需要用设计模式就好了&#xff0c;而大佬们考虑的就多了&#xff0c;这些设计模式就像棋谱&#xff0c;只要按照棋谱来下&am…

能源物联网数据采集网关 多协议对接解决方案

安科瑞刘鸿鹏 摘要 随着配电系统智能化需求的提升&#xff0c;现代配电物联网&#xff08;IoT&#xff09;系统对数据采集、传输、处理及远程管理能力提出了更高要求。智能网关作为连接现场设备与上层管理平台的核心枢纽&#xff0c;其性能直接影响系统的实时性、可靠性与扩展…

Node.js 中的 Event 模块详解

Node.js 中的 Event 模块是实现事件驱动编程的核心模块。它基于观察者模式&#xff0c;允许对象&#xff08;称为“事件发射器”&#xff09;发布事件&#xff0c;而其他对象&#xff08;称为“事件监听器”&#xff09;可以订阅并响应这些事件。这种模式非常适合处理异步操作和…

Unity开发抖音小游戏播放视频

Unity开发抖音小游戏播放视频 介绍抖音小程序ios端视频无法播放RenderTexture问题总结 介绍 最近在做抖音小游戏播放视频&#xff0c;这里我使用的是Unity原生的VideoPlayer组件来播放视频&#xff0c;这里总结了一下我相关的报错以及能够正常播放视频的代码。如果还不知道怎么…

网络安全抑制 缓解 根除 恢复 网络安全如何解决

一、网络安全 网络是指网络系统的硬件、软件及其系统中的数据受到保护&#xff0c;不因偶然的或者恶意的原因而遭受到破坏、更改、泄露&#xff0c;系统连续可靠正常地运行&#xff0c;网络服务不中断。 二、如何防范网络安全问题 1、防范网络病毒。 2、配置防火墙。 3、采…

自有证书的rancher集群使用rke部署k8s集群异常

rancher使用自签域名&#xff0c;或者商业证书容易踩到的坑。 最开始的报错&#xff1a; docker logs kubelet‘s id E0214 13:04:14.590268 9614 pod_workers.go:1300] "Error syncing pod, skipping" err"failed to \"StartContainer\" for …

开源的轻量级分布式文件系统FastDFS

FastDFS 是一个开源的轻量级分布式文件系统&#xff0c;专为高性能的分布式文件存储设计&#xff0c;主要用于解决海量文件的存储、同步和访问问题。它特别适合以中小文件&#xff08;如图片、视频等&#xff09;为载体的在线服务&#xff0c;例如相册网站、视频网站等。 FastD…

Github 2025-02-12 C开源项目日报 Top7

根据Github Trendings的统计,今日(2025-02-12统计)共有7个项目上榜。根据开发语言中项目的数量,汇总情况如下: 开发语言项目数量C项目7Python项目2OpenSSL - 强大的开源加密工具包 创建周期:4012 天开发语言:C协议类型:Apache License 2.0Star数量:23449 个Fork数量:10…

深入浅出:Python 中的异步编程与协程

引言 大家好&#xff0c;今天我们来聊聊 异步编程 和 协程&#xff0c;这是近年来编程语言领域中的热点话题之一&#xff0c;尤其在 Python 中&#xff0c;它作为一种全新的编程模型&#xff0c;已经成为处理 IO密集型 任务的强力工具。尽管很多人对异步编程望而却步&#xff0…

高级 Conda 使用:环境导出、共享与优化

1. 引言 在 Conda 的基础包管理功能中&#xff0c;我们了解了如何安装、更新和卸载包。但对于开发者来说&#xff0c;如何更好地管理环境、导出环境配置、共享环境&#xff0c;以及如何优化 Conda 的使用效率&#xff0c;才是提高工作效率的关键。本篇博客将进一步深入 Conda …

三十一、micro-app踩坑

版本:0.8.6 1.子应用单独运行正常,基座加载子应用后接口404 原因:子应用请求的接口为相对地址,会以基座域名进行补全,导致报错。 解决方法:

MATLAB中isfield函数用法

目录 语法 说明 示例 确定输入名称是否为字段名称 isfield函数的功能是确定输入是否为结构体数组字段。 语法 TF isfield(S,field) 说明 如果 field 是结构体数组 S 的一个字段的名称&#xff0c;则 TF isfield(S,field) 返回 1。否则&#xff0c;将返回 0。 如果 fie…

在Autonomous DB中创建训练数据集

在Autonomous DB中创建训练数据集 概述背景步骤解析1. 定义公司术语表2. 使用SQL将数据转换为JSON格式3. 使用SPool命令将SQL查询结果输出为JSON文件4. 查看生成的JSON文件 结果示例结论 概述 在机器学习中&#xff0c;构建高质量的训练数据集是模型成功的关键&#xff0c;尤其…

ASP.NET Core 使用 FileStream 将 FileResult 文件发送到浏览器后删除该文件

FileStream 在向浏览器发送文件时节省了服务器内存和资源&#xff0c;但如果需要删除文件怎么办&#xff1f;本文介绍如何在发送文件后删除文件&#xff1b;用 C# 编写。 另请参阅&#xff1a;位图创建和下载 使用FileStream向浏览器发送数据效率更高&#xff0c;因为文件是从…

深入理解 Qt 信号与槽机制:原理、用法与优势

一、信号与槽的概念 在 Qt 编程中&#xff0c;信号与槽机制是实现对象间通信的核心工具。 信号&#xff1a;本质上是一种特殊的成员函数声明&#xff0c;它不包含函数体&#xff0c;仅用于通知其他对象某一事件的发生。例如&#xff0c;当用户点击界面上的按钮时&#xff0c;…

蓝桥杯(B组)-每日一题

题目&#xff1a; 思路&#xff1a; 首先将所有牛分类 1.a第一头母牛-每年年初生一头小母牛 2.不能生小牛的牛&#xff1a; b1-一岁小母牛 b2-二岁小母牛 b3-三岁小母牛 超过4岁就会再生一头小牛 因此计算每年生的小牛是第一头生的a再加上4岁后的生的 代码实现&#xff1…

处理项目中存在多个版本的jsqlparser依赖

异常提示 Correct the classpath of your application so that it contains a single, compatible version of net.sf.jsqlparser.statement.select.SelectExpressionIte实际问题 原因&#xff1a;项目中同时使用了 mybatis-plus 和 pagehelper&#xff0c;两者都用到了 jsqlpa…

Spring Boot 常用依赖详解:如何选择和使用常用依赖

在Spring Boot项目中&#xff0c;依赖&#xff08;Dependencies&#xff09;是项目的核心组成部分。每个依赖都提供了一些特定的功能或工具&#xff0c;帮助我们快速开发应用程序。本文将详细介绍Spring Boot中常用的依赖及其作用&#xff0c;并指导你如何根据项目需求选择合适…

模糊综合评价法:原理、步骤与MATLAB实现

引言 在复杂决策场景中&#xff0c;评价对象往往涉及多个相互关联的模糊因素。模糊综合评价法通过建立模糊关系矩阵&#xff0c;结合权重分配与合成算子&#xff0c;实现对多因素系统的科学评价。本文详细讲解模糊综合评价法的数学原理、操作步骤&#xff0c;并辅以MATLAB代码…