QT设计模式:备忘录模式

备忘录模式(Memento Pattern)是一种行为型设计模式,主要用于保存一个对象当前的状态,并在需要时恢复该状态。它常应用于以下场景:

  1. 撤销操作:如文本编辑器撤销、软件开发中的版本控制等,用户可以返回到之前的状态。
  2. 备份和恢复:系统故障时,使用备份数据恢复到之前的状态,减少数据丢失风险。
  3. 系统快照:在执行高风险操作之前,创建系统状态的快照,方便后续进行回滚操作。

备忘录模式主要有三个参与者:发起人(Originator)、备忘录(Memento)和负责人(Caretaker)。发起人负责创建备忘录和恢复状态;备忘录负责存储发起人的状态信息;负责人管理多个备忘录。

QT示例:

Memento:增加一个Memento类去记录QTextEdit的字体和颜色

MyCommand类:对应备忘录模式的Originator(发起人);

QUndoStack类:对应 Caretaker(负责人),负责管理撤销和重做操作,维护命令的历史记录。

#include <QApplication>
#include <QTextEdit>
#include <QUndoStack>
#include <QPushButton>
#include <QVBoxLayout>
#include <QUndoCommand>class Memento {
public:Memento(const QString &text, const QFont &font, const QColor &color): m_text(text), m_font(font), m_color(color) {}const QString& getText() const { return m_text; }const QFont& getFont() const { return m_font; }const QColor& getColor() const { return m_color; }private:QString m_text;QFont m_font;QColor m_color;
};class QUndoCommand
{
public:virtual ~QUndoCommand() {}virtual void undo() = 0;virtual void redo() = 0;
};class MyCommand : public QUndoCommand {
public:MyCommand(QTextEdit *editor, const QString &text, const QFont &font, const QColor &color, QUndoCommand *parent = nullptr): QUndoCommand(parent), m_editor(editor),m_newMemento(std::make_shared<Memento>(text, font, color)) {m_oldMemento = std::make_shared<Memento>(editor->toPlainText(), editor->font(), editor->textColor());}void undo() override {m_editor->setPlainText(m_oldMemento->getText());m_editor->setFont(m_oldMemento->getFont());m_editor->setTextColor(m_oldMemento->getColor());}void redo() override {m_editor->setPlainText(m_newMemento->getText());m_editor->setFont(m_newMemento->getFont());m_editor->setTextColor(m_newMemento->getColor());}private:QTextEdit *m_editor;std::shared_ptr<Memento> m_newMemento;std::shared_ptr<Memento> m_oldMemento;
};class QUndoStack
{
public:void push(QUndoCommand *cmd){m_stack.push(cmd);cmd->redo();}void undo(){if (!m_stack.isEmpty()) {QUndoCommand *cmd = m_stack.pop();cmd->undo();m_undoStack.push(cmd);}}void redo(){if (!m_undoStack.isEmpty()) {QUndoCommand *cmd = m_undoStack.pop();cmd->redo();m_stack.push(cmd);}}private:QStack<QUndoCommand*> m_stack;QStack<QUndoCommand*> m_undoStack;
};int main(int argc, char **argv) {QApplication app(argc, argv);QUndoStack stack;QTextEdit editor;QPushButton undoButton("Undo");QPushButton redoButton("Redo");QObject::connect(&undoButton, &QPushButton::clicked, &stack, &QUndoStack::undo);QObject::connect(&redoButton, &QPushButton::clicked, &stack, &QUndoStack::redo);// 假设用户通过一些方式,可以更改QTextEdit的字体和颜色QObject::connect(&editor, &QTextEdit::cursorPositionChanged, [&]() {QFont font = editor->font();QColor color = editor->textColor();stack.push(new MyCommand(&editor, editor.toPlainText(), font, color));});QVBoxLayout layout;layout.addWidget(&editor);layout.addWidget(&undoButton);layout.addWidget(&redoButton);QWidget window;window.setLayout(&layout);window.show();return app.exec();
}

在这个示例中,我们假设用户可以通过一些方式,可以更改QTextEdit的字体和颜色,并且这也需要做到撤销和重做。我们如果结合使用备忘录模式,增加一个Memento类去记录QTextEdit的字体和颜色,那么这个过程就简单的多了。否则,MyCommand类需要存储所有的状态,如果状态相关的数据对象越来越多,可能会导致MyCommand类的职责过重。

在这里,MyCommand类兼任了备忘录模式的Originator类和命令模式的Receiver类,QUndoStack类兼任了备忘录模式的Caretaker类和命令模式的Invoker类。所以实际上,命令模式和备忘录模式,可以简单理解为在命令模式的基础上增加一个Memento类就可以了。

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

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

相关文章

差分总结(一维+二维)

差分&#xff0c;可以视作前缀和的逆运算。 前缀和用于去求一个区间段的和 差分用于改变一个区间的值&#xff08;比如说某个区间都加上或者减去一个数&#xff09; P2367 语文成绩 #include<bits/stdc.h> using namespace std; #define int long long int n,p; int a…

RabbitMQ 学习笔记

RabbitMQ学习笔记 一些概念 Broker &#xff1a;RabbitMQ服务。 virtual host&#xff1a; 其实就是分组。 Connection&#xff1a;连接&#xff0c;生产者消费者与Broker之间的TCP连接。 Channel&#xff1a;网络信道&#xff0c;轻量级的Connection&#xff0c;使用Chann…

2024广东省职业技能大赛云计算赛项实战——Minio服务搭建

Minio服务搭建 前言 这道题是比赛时考到的&#xff0c;没找到具体题目&#xff0c;但在公布的样题中找到了&#xff0c;虽然很短~ 使用提供的 OpenStack 云平台&#xff0c;申请一台云主机&#xff0c;使用提供的软件包安装部署 MINIO 服务并使用 systemctl 管理 Minio是一个…

HTML静态网页成品作业(HTML+CSS)——手机电子商城网页(4个页面)

&#x1f389;不定期分享源码&#xff0c;关注不丢失哦 文章目录 一、作品介绍二、作品演示三、代码目录四、网站代码HTML部分代码 五、源码获取 一、作品介绍 &#x1f3f7;️本套采用HTMLCSS&#xff0c;未使用Javacsript代码&#xff0c;共有4个页面。 二、作品演示 三、代…

Vue 封装组件之Input框

封装Input组件:MyInput.vue <template><div class"base-input-wraper"><el-inputv-bind"$attrs"v-on"$listeners"class"e-input":style"inputStyle":value"value":size"size"input&quo…

深入解析微软Edge浏览器:探索其功能与应用

微软Edge浏览器是微软公司推出的一款现代化网页浏览器,旨在为用户提供快速、安全和高效的上网体验。本文将全面解析微软Edge浏览器,从其历史背景、核心功能、性能表现、安全特性到实际应用场景,带领读者深入了解这款浏览器的优势和使用技巧。 一、Edge浏览器的历史背景 1.…

python API自动化(Pytest+Excel+Allure完整框架集成+yaml入门+大量响应报文处理及加解密、签名处理)

1.pytest数据参数化 假设你需要测试一个登录功能&#xff0c;输入用户名和密码后验证登录结果。可以使用参数化实现多组输入数据的测试: 测试正确的用户名和密码登录成功 测试正确的用户名和错误的密码登录失败 测试错误的用户名和正确的密码登录失败 测试错误的用户名和密码登…

转换普通文件为Spring中的MultipartFile类型:处理不同文件格式

在Web开发中&#xff0c;处理文件上传是一个常见的需求。有时&#xff0c;我们需要将普通的文件对象&#xff08;如.txt或.xlsx文件&#xff09;转换为Spring框架中的MultipartFile类型&#xff0c;以便在Controller中处理文件上传和处理。本文将介绍如何在Java中进行这种转换&…

2024广东省职业技能大赛云计算赛项实战——chkrootkit安装与使用

chkrootkit安装与使用 前言 在今年比赛中有考到这样一道题&#xff0c;也是在公布的样卷中找到了它&#xff0c;今天就做做它并讲解一下&#xff1a; 公有云安全&#xff1a;入侵检测系统 使用提供的 makechk.tar.gz 包安装 chkrootkit 入侵检测工具&#xff0c;安装完毕后使…

音乐界的颠覆与挑战分析

最近的一个月&#xff0c;音乐界掀起了一场科技革命。一系列音乐大模型轮番上线&#xff0c;将素人生产音乐的门槛降到了最低。这一系列科技产品&#xff0c;不仅引发了大众对音乐产业未来发展的热烈讨论&#xff0c;也带来了新的挑战和问题。  一方面&#xff0c;这些AI音乐…

定时器-前端使用定时器3s轮询状态接口,2min为接口超时

背景 众所周知&#xff0c;后端是处理不了复杂的任务的&#xff0c;所以经过人家的技术讨论之后&#xff0c;把业务放在前端来实现。记录一下这次的离大谱需求吧。 如图所示&#xff0c;这个页面有5个列表&#xff0c;默认加载计划列表。但是由于后端的种种原因&#xff0c;这…

PHP XML: 解析、生成与操作指南

PHP XML: 解析、生成与操作指南 PHP,作为一种流行的服务器端脚本语言,提供了强大的功能来处理XML(可扩展标记语言)数据。XML是一种用于存储和传输数据的标记语言,它通过标签来标识数据。在Web开发中,XML常用于数据交换、配置文件和结构化文档。本文将详细介绍如何使用PH…

C++ | Leetcode C++题解之第171题Excel表列序号

题目&#xff1a; 题解&#xff1a; class Solution { public:int titleToNumber(string columnTitle) {int number 0;long multiple 1;for (int i columnTitle.size() - 1; i > 0; i--) {int k columnTitle[i] - A 1;number k * multiple;multiple * 26;}return num…

QT中利用QMovie实现动态加载效果

1、效果 2、代码 #include "widget.h" #include "ui_widget.h" #include <QLabel> #include <QMovie>

【Python Cookbook】S02E15 在文本中处理 HTML 和 XML 实体

目录 问题解决方案讨论 问题 我们如果想要将 HTML 实体以及 XML 实体内容替换成相对应的文本内容&#xff0c;怎么做&#xff1f; 解决方案 s "Elements are written as <tag>txt</tag>."import html print(html.escape(s)) print("-"*20,…

数据分析中如何理解透视表

透视表&#xff08;Pivot Table&#xff09;是数据分析中一种非常强大的工具&#xff0c;用于快速汇总、分析、探索和展示数据。透视表可以根据数据的不同维度和指标进行重组和计算&#xff0c;帮助用户从大量数据中提取有用的信息和发现数据中的模式和趋势。 透视表的基本概念…

在服务器上搭配大模型的运行环境详细版(docker+ollama+langchain等工具)

用到的工具 1.anaconda3环境安装 anaconda3导出环境 #导出环境 conda env export --name your_env_name > custom_environment.yaml #导入环境 conda env create -f environment.yaml2.前置的docker软件安装、docker镜像如何进行转移 sudo apt-get update #时期能访问阿…

在Linux/Ubuntu/Debian中使用SSH连接远程服务器VPS

在Linux/Ubuntu/Debian中使用SSH连接远程服务器VPS 在远程管理服务器时&#xff0c;SSH&#xff08;Secure Shell&#xff09;协议是我们常用的工具之一。它提供了一种加密的方式来访问和管理远程主机。默认情况下&#xff0c;SSH使用22端口&#xff0c;但有时我们需要通过指定…

Redisson-DelayedQueue-原理

归档 GitHub: Redisson-DelayedQueue-原理 Unit-Test RedissonDelayedQueueTest 常规测试 Test public void testCommon() throws InterruptedException {RBlockingQueue<String> destinationQueue redisson.getBlockingQueue("delay_queue"); // 目标队…

YOLOv10训练自己的数据集(图像目标检测)

目录 1、下载代码 2、环境配置 3、准备数据集 4、yolov10训练 可能会出现报错&#xff1a; 1、下载代码 源码地址&#xff1a;https://github.com/THU-MIG/yolov10 2、环境配置 打开源代码&#xff0c;在Terminal中&#xff0c;使用conda 创建虚拟环境配置 命令如下&a…