当前位置: 首页 > news >正文

Swift Combine 有序的异步操作 从入门到精通十二

Combine 系列

  1. Swift Combine 从入门到精通一
  2. Swift Combine 发布者订阅者操作者 从入门到精通二
  3. Swift Combine 管道 从入门到精通三
  4. Swift Combine 发布者publisher的生命周期 从入门到精通四
  5. Swift Combine 操作符operations和Subjects发布者的生命周期 从入门到精通五
  6. Swift Combine 订阅者Subscriber的生命周期 从入门到精通六
  7. Swift 使用 Combine 进行开发 从入门到精通七
  8. Swift 使用 Combine 管道和线程进行开发 从入门到精通八
  9. Swift Combine 使用 sink, assign 创建一个订阅者 从入门到精通九
  10. Swift Combine 使用 dataTaskPublisher 发起网络请求 从入门到精通十
  11. Swift Combine 用 Future 来封装异步请求 从入门到精通十一
    在这里插入图片描述

目的:使用 Combine 的管道来显式地对异步操作进行排序

这类似于一个叫做 “promise chaining” 的概念。 虽然你可以将 Combine 处理的和其行为一致,但它可能不能良好地替代对 promise 库的使用。 主要区别在于,promise 库总是将每个 promise 作为单一结果处理,而 Combine 带来了可能需要处理许多值的复杂性。

任何需要按特定顺序执行的异步(或同步)任务组都可以使用 Combine 管道进行协调管理。 通过使用 Future 操作符,可以捕获完成异步请求的行为,序列操作符提供了这种协调功能的结构。

通过将任何异步 API 请求与 Future 发布者进行封装,然后将其与 flatMap 操作符链接在一起,你可以以特定顺序调用被封装的异步 API 请求。 通过使用 Future 或其他发布者创建多个管道,使用 zip 操作符将它们合并之后等待管道完成,通过这种方法可以创建多个并行的异步请求。

如果你想强制一个 Future 发布者直到另一个发布者完成之后才被调用,你可以把 future 发布者创建在 flatMap 的闭包中,这样它就会等待有值被传入 flatMap 操作符之后才会被创建。

通过组合这些技术,可以创建任何并行或串行任务的结构。

如果后面的任务需要较早任务的数据,这种协调异步请求的技术会特别有效。 在这些情况下,所需的数据结果可以直接通过管道传输。

此排序的示例如下。 在此示例中,按钮在完成时会高亮显示,按钮的排列顺序是特意用来显示操作顺序的。 整个序列由单独的按钮操作触发,该操作还会重置所有按钮的状态,如果序列中有尚未完成的任务,则都将被取消。 在此示例中,异步 API 请求会在随机的时间之后完成,作为例子来展示时序的工作原理。

创建的工作流分步表示如下:

  • 步骤 1 先运行。
  • 步骤 2 有三个并行的任务,在步骤 1 完成之后运行。
  • 步骤 3 等步骤 2 的三个任务全部完成之后,再开始执行。
  • 步骤 4 在步骤 3 完成之后开始执行。

此外,还有一个 activity indicator 被触发,以便在序列开始时开始动画,在第 4 步完成时停止。

UIKit-Combine/AsyncCoordinatorViewController.swift

import UIKit
import Combineclass AsyncCoordinatorViewController: UIViewController {@IBOutlet weak var startButton: UIButton!@IBOutlet weak var step1_button: UIButton!@IBOutlet weak var step2_1_button: UIButton!@IBOutlet weak var step2_2_button: UIButton!@IBOutlet weak var step2_3_button: UIButton!@IBOutlet weak var step3_button: UIButton!@IBOutlet weak var step4_button: UIButton!@IBOutlet weak var activityIndicator: UIActivityIndicatorView!var cancellable: AnyCancellable?var coordinatedPipeline: AnyPublisher<Bool, Error>?@IBAction func doit(_ sender: Any) {runItAll()}func runItAll() {if self.cancellable != nil {  // 1print("Cancelling existing run")cancellable?.cancel()self.activityIndicator.stopAnimating()}print("resetting all the steps")self.resetAllSteps()  // 2// driving it by attaching it to .sinkself.activityIndicator.startAnimating()  // 3print("attaching a new sink to start things going")self.cancellable = coordinatedPipeline?  // 4.print().sink(receiveCompletion: { completion inprint(".sink() received the completion: ", String(describing: completion))self.activityIndicator.stopAnimating()}, receiveValue: { value inprint(".sink() received value: ", value)})}// MARK: - helper pieces that would normally be in other files// this emulates an async API call with a completion callback// it does nothing other than wait and ultimately return with a boolean valuefunc randomAsyncAPI(completion completionBlock: @escaping ((Bool, Error?) -> Void)) {DispatchQueue.global(qos: .background).async {sleep(.random(in: 1...4))completionBlock(true, nil)}}/// Creates and returns pipeline that uses a Future to wrap randomAsyncAPI/// and then updates a UIButton to represent the completion of the async/// work before returning a boolean True./// - Parameter button: button to be updatedfunc createFuturePublisher(button: UIButton) -> AnyPublisher<Bool, Error> {  // 5return Future<Bool, Error> { promise inself.randomAsyncAPI() { (result, err) inif let err = err {promise(.failure(err))} else {promise(.success(result))}}}.receive(on: RunLoop.main)// so that we can update UI elements to show the "completion"// of this step.map { inValue -> Bool in  // 6// intentionally side effecting here to show progress of pipelineself.markStepDone(button: button)return true}.eraseToAnyPublisher()}/// highlights a button and changes the background color to green/// - Parameter button: reference to button being updatedfunc markStepDone(button: UIButton) {button.backgroundColor = .systemGreenbutton.isHighlighted = true}func resetAllSteps() {for button in [self.step1_button, self.step2_1_button, self.step2_2_button, self.step2_3_button, self.step3_button, self.step4_button] {button?.backgroundColor = .lightGraybutton?.isHighlighted = false}self.activityIndicator.stopAnimating()}// MARK: - view setupoverride func viewDidLoad() {super.viewDidLoad()self.activityIndicator.stopAnimating()// Do any additional setup after loading the view.coordinatedPipeline = createFuturePublisher(button: self.step1_button)  // 7.flatMap { flatMapInValue -> AnyPublisher<Bool, Error> inlet step2_1 = self.createFuturePublisher(button: self.step2_1_button)let step2_2 = self.createFuturePublisher(button: self.step2_2_button)let step2_3 = self.createFuturePublisher(button: self.step2_3_button)return Publishers.Zip3(step2_1, step2_2, step2_3).map { _ -> Bool inreturn true}.eraseToAnyPublisher()}.flatMap { _ inreturn self.createFuturePublisher(button: self.step3_button)}.flatMap { _ inreturn self.createFuturePublisher(button: self.step4_button)}.eraseToAnyPublisher()}
}
  1. runItAll 协调此工作流的进行,它从检查当前是否正在执行开始。 如果是,它会在当前的订阅者上调用 cancel()
  2. resetAllSteps 通过遍历所有表示当前工作流状态的按钮,并将它们重置为灰色和未高亮以回到初始状态。 它还验证 activity indicator 当前未处于动画中。
  3. 然后我们开始执行请求,首先开启 activity indicator 的旋转动画。
  4. 使用 sink 创建订阅者并存储对工作流的引用。 被订阅的发布者是在该函数外创建的,允许被多次复用。 管道中的 print 操作符用于调试,在触发管道时在控制台显示输出。
  5. 每个步骤都由 Future 发布者紧跟管道构建而成,然后立即由管道操作符切换到主线程,然后更新 UIButton 的背景色,以显示该步骤已完成。 这封装在 createFuturePublisher 的调用中,使用 eraseToAnyPublisher 以简化返回的类型。
  6. map 操作符用于创建并更新 UIButton,作为特定的效果以显示步骤已完成。
  7. 创建整个管道及其串行和并行任务结构,是结合了对 createFuturePublisher 的调用以及对 flatMapzip 操作符的使用共同完成的。

另请参阅

  • 通过包装基于 delegate 的 API 创建重复发布者
  • 使用此代码的 ViewController 在 github 的项目中 UIKit-Combine/AsyncCoordinatorViewController.swift.

参考

https://heckj.github.io/swiftui-notes/index_zh-CN.html

代码

https://github.com/heckj/swiftui-notes

相关文章:

Swift Combine 有序的异步操作 从入门到精通十二

Combine 系列 Swift Combine 从入门到精通一Swift Combine 发布者订阅者操作者 从入门到精通二Swift Combine 管道 从入门到精通三Swift Combine 发布者publisher的生命周期 从入门到精通四Swift Combine 操作符operations和Subjects发布者的生命周期 从入门到精通五Swift Com…...

国产航顺HK32F030M: 超声波测距模块串口通信数据接收与处理

参考代码 /************************************************************************************************** * file usart_async_tx_no_int_rx_rxneint.c * brief 异步串口通信例程, 通过查询TXE标志发送数据,通过RXNE中断接收数据,当中断接收到数据后会将 * …...

idea:如何连接数据库

1、在idea中打开database: 2、点击 ‘’ ---> Data Source ---> MySQL 3、输入自己的账号和密码其他空白处可以不填&#xff0c;用户和密码可以在自己的mysql数据库中查看 4、最后选择自己需要用的数据库&#xff0c;点击运用ok&#xff0c;等待刷新即可 最后&#xff1a…...

JS中ES5和ES6的区别

前言 ES5是JavaScript的第五个修订版本&#xff0c;于2009年发布。而ES6是JavaScript的第六个修订版本&#xff0c;也称为ES2015&#xff0c;于2015年发布。以下是它们两个版本之前的一些区别&#xff1a; 变量声明方式 在ES5中&#xff0c;使用var关键字进行变量声明&#…...

软考24-上午题-图1

一、数据结构的回忆 线性结构&#xff1a;&#xff08;一对一&#xff09; 除首结点没有前驱、末尾结点没有后继外&#xff0c;一个结点只有唯一的一个直接前驱和唯一的一个直接后继。 树结构&#xff1a;&#xff08;一对多&#xff09; 除根节点没有前驱节点外&#xff0c;…...

书生·浦语大模型第四课作业

基础作业&#xff1a; 构建数据集&#xff0c;使用 XTuner 微调 InternLM-Chat-7B 模型, 让模型学习到它是你的智能小助手&#xff0c;效果如下图所示&#xff0c;本作业训练出来的模型的输出需要将不要葱姜蒜大佬替换成自己名字或昵称&#xff01; 1.安装 # 如果你是在 Int…...

勒索攻击风起云涌,Sodinokibi深度分析

前言 Sodinokibi勒索病毒&#xff0c;又称为REvil勒索病毒&#xff0c;这款勒索病毒最早在国内被发现是2019年4月份&#xff0c;笔者在早期分析这款勒索病毒的时候就发现它与其他勒索病毒不同&#xff0c;于是被笔者称为GandCrab勒索病毒的“接班人”&#xff0c;为什么它是Ga…...

1124. 骑马修栅栏(欧拉路径,模板)

农民John每年有很多栅栏要修理。 他总是骑着马穿过每一个栅栏并修复它破损的地方。 John是一个与其他农民一样懒的人。 他讨厌骑马&#xff0c;因此从来不两次经过一个栅栏。 你必须编一个程序&#xff0c;读入栅栏网络的描述&#xff0c;并计算出一条修栅栏的路径&#xf…...

C# CAD2016获取数据操作BlockTableRecord、Polyline、DBObject

一、数据操作说明 //DBObject 基础类 DBObject dbObj (DBObject)tr.GetObject(outerId, OpenMode.ForRead); //Polyline 线段类 Polyline outerPolyline (Polyline)tr.GetObject(outerId, OpenMode.ForRead); //BlockTableRecord 块表类 BlockTableRecord modelSpace (Bloc…...

java SSM新闻管理系统myeclipse开发mysql数据库springMVC模式java编程计算机网页设计

一、源码特点 java SSM新闻管理系统是一套完善的web设计系统&#xff08;系统采用SSM框架进行设计开发&#xff0c;springspringMVCmybatis&#xff09;&#xff0c;对理解JSP java编程开发语言有帮助&#xff0c;系统具有完整的源代码和数据库&#xff0c;系统主要采用B/S…...

Linux_线程

线程与进程 多级页表 线程控制 线程互斥 线程同步 生产者消费者模型 常见概念 下面选取32位系统举例。 一.线程与进程 上图是曾经我们认为进程所占用的资源的集合。 1.1 线程概念 线程是一个执行分支&#xff0c;执行粒度比进程细&#xff0c;调度成本比进程低线程是cpu…...

【selenium】

selenium是一个Web的自动化测试工具&#xff0c;最初是为网站自动化测试而开发的。Selenium可以直接调用浏览器&#xff0c;它支持所有主流的浏览器。其本质是通过驱动浏览器&#xff0c;完成模拟浏览器操作&#xff0c;比如挑战&#xff0c;输入&#xff0c;点击等。 下载与打…...

HX711压力传感器学习一(STM32)

目录 原理图&#xff1a;​ 引脚介绍&#xff1a; HX711介绍工作原理: 程序讲解&#xff1a; 整套工程&#xff1a; 发送的代码工程&#xff0c;与博客的不一致&#xff0c;如果编译有报错请按照报错和博客进行修改 原理图&#xff1a; 引脚介绍&#xff1a; VCC和GND引…...

作业2.13

1、选择题 1.1、若有定义语句&#xff1a;int a[3][6]; &#xff0c;按在内存中的存放顺序&#xff0c;a 数组的第10个元素是 D A&#xff09;a[0][4] B) a[1][3] C)a[0][3] D)a[1][4] 1.2、有数组 int a[5] {10&#xff0c;20&#xff0c;30&#xff0c;40&#xff0c;50},…...

ArcGIS学习(七)图片数据矢量化

ArcGIS学习(七)图片数据矢量化 通过上面几个任务的学习,大家应该已经掌握了ArcGIS的基础操作,并且学习了坐标系和地理数据库这两个非常重要且稍微难一些的专题。从这一任务开始,让我们进入到实战案例板块。 首先进入第一个案例一一图片数据矢量化。 我们在平时的工作学…...

G口大流量服务器选择的关键点有哪些?

G口服务器指的是接入互联网的带宽达到1Gbps以上的服务器&#xff0c;那么选择使用G口大流量服务器的用户需要注意哪些选择 关键点呢?小编为您整理关于G口大流量服务器的关键点。 G口服务器通常被用于需要大带宽支持的业务场景&#xff0c;比如视频流媒体、金融交易平台、电子商…...

MongoDB聚合:$unset

使用$unset阶段可移除文档中的某些字段。从版本4.2开始支持。 语法 移除单个字段&#xff0c;可以直接指定要移除的字段名&#xff1a; { $unset: "<field>" }移除多个字段&#xff0c;可以指定一个要移除字段名的数组&#xff1a; { $unset: [ "<…...

DS Wannabe之5-AM Project: DS 30day int prep day14

Q1. What is Alexnet? Q2. What is VGGNet? Q3. What is VGG16? Q4. What is ResNet? At the ILSVRC 2015, so-called Residual Neural Network (ResNet) by the Kaiming He et al introduced the anovel architecture with “skip connections” and features heavy b…...

【程序设计竞赛】C++与Java的细节优化

必须强调下&#xff0c;以下的任意一种优化&#xff0c;都应该是在本身采用的算法没有任何问题情况下的“锦上添花”&#xff0c;而不是“雪中送炭”。 如果下面的说法存在误导&#xff0c;请专业大佬评论指正 读写优化 C读写优化——解除流绑定 在ACM里&#xff0c;经常出现…...

Java缓冲流——效率提升深度解析

前言 大家好&#xff0c;我是chowley&#xff0c;在我之前的项目中&#xff0c;用到了缓冲流来提高字符流之间的比较速度&#xff0c;缓冲流的主要作用类似于数据库缓存&#xff0c;提高IO操作效率。 缓冲流 在Java的输入输出操作中&#xff0c;缓冲流是提高性能的重要工具之…...

16 亚稳态原理和解决方案

1. 亚稳态原理 亚稳态是指触发器无法在某个规定的时间段内到达一个可以确认的状态。在同步系统中&#xff0c;输入总是与时钟同步&#xff0c;因此寄存器的setup time和hold time是满足的&#xff0c;一般情况下是不会发生亚稳态情况的。在异步信号采集中&#xff0c;由于异步…...

C# OCR识别图片中的文字

1、从NuGet里面安装Spire.OCR 2、安装之后&#xff0c;找到安装路径下&#xff0c;默认生成的packages文件夹&#xff0c;复制该文件夹路径下的 6 个dll文件到程序的根目录 3、调用读取方法 OcrScanner scanner new OcrScanner(); string path "C:\1.png"; scann…...

使用python-numpy实现一个简单神经网络

目录 前言 导入numpy并初始化数据和激活函数 初始化学习率和模型参数 迭代更新模型参数&#xff08;权重&#xff09; 小彩蛋 前言 这篇文章&#xff0c;小编带大家使用python-numpy实现一个简单的三层神经网络&#xff0c;不使用pytorch等深度学习框架&#xff0c;来理解…...

CSS定位装饰

网页常见布局方式 标准流 块级元素独占一行---垂直布局 行内元素/行内块元素一行显示多个----水平布局 浮动 可以让原本垂直布局的块级元素变成水平布局 定位 可以让元素自由的摆放在网页的任意位置 一般用于盒子之间的层叠情况 使用定位步骤 设置定位方式 属性名&am…...

java之jvm详解

JVM内存结构 程序计数器 Program Counter Register程序计数器(寄存器) 程序计数器在物理层上是通过寄存器实现的 作用&#xff1a;记住下一条jvm指令的执行地址特点 是线程私有的(每个线程都有属于自己的程序计数器)不会存在内存溢出 虚拟机栈(默认大小为1024kb) 每个线…...

vue3学习——集成sass

安装 pnpm i sass sass-loader -D在vite.config.ts文件配置: export default defineConfig({css: {preprocessorOptions: {scss: {javascriptEnabled: true,additionalData: import "./src/styles/variable.scss";,},},},} }创建三个文件 src/styles/index.scss //…...

开关电源学习之Boost电路

如果我们需要给一个输入电压为5V的芯片供电&#xff0c;而我们只有一个3.3V的电源&#xff0c;那怎么办&#xff1f; 我们能不能把3.3V的电压升到5V&#xff1f; 一、电感的简介 而在升压的电路设计方案中&#xff0c;使用到一个重要的元器件&#xff1a;电感。 电感的特性…...

QRegExp的学习

【QT学习】QRegExp类正则表达式&#xff08;一文读懂&#xff09;-CSDN博客 [ ]:匹配括号内输入的任意字符 例&#xff1a;[123]:可以是1或2或3 {m&#xff0c;n}表达式至少重复m次&#xff0c;至多重复n次。 例&#xff1a;"ba{1,3}"可以匹配 "ba"或&…...

28.Stream流

Stream流 1. 概述2. 方法2.1 开始生成方法2.1.1 概述2.1.2 方法2.1.3 代码示例 2.2 中间操作方法2.2.1 概述2.2.2 方法2.2.3 代码示例 2.3 终结操作方法2.3.1 概述2.3.2 方法2.3.3 代码示例 2.4 收集操作方法2.4.1 概述2.4.2 方法2.4.3 代码示例 3. 代码示例14. 代码示例25. 代…...

大数据应用对企业的价值

目录 一、大数据应用价值 1.1 大数据技术分析 1.2 原有技术场景的优化 1.2.1 数据分析优化 1.2.2 高并发数据处理 1.3 通过大数据构建新需求 1.3.1 智能推荐 1.3.2 广告系统 1.3.3 产品/流程优化 1.3.4 异常检测 1.3.5 智能管理 1.3.6 人工智能和机器学习 二、大数…...

【51单片机】LED点阵屏(江科大)

9.1LED点阵屏 1.LED点阵屏介绍 LED点阵屏由若干个独立的LED组成,LED以矩阵的形式排列,以灯珠亮灭来显示文字、图片、视频等。 2.LED点阵屏工作原理 LED点阵屏的结构类似于数码管,只不过是数码管把每一列的像素以“8”字型排列而已。原理图如下 每一行的阳极连在一起,每一列…...

Microsoft OneNote 图片文字提取

Microsoft OneNote 图片文字提取 1. 文件 -> 新建 -> 我的电脑 -> 名称 -> 位置 -> 创建笔记本2. 插入图片​​​3. 复制图片中的文本References 1. 文件 -> 新建 -> 我的电脑 -> 名称 -> 位置 -> 创建笔记本 ​ 2. 插入图片 ​​​3. 复制图片…...

Linux系统安全——iptables相关总结

在使用iptables时注意要先关闭firewalld&#xff08;systemctl stop firewalld.service&#xff09; 1.查看iptables规则 iptables -vnL 选项含义-v查看时显示更多详细信息-n所有字段以数字形式显示-L查看规则列表 例&#xff0c;拒绝来自192.168.241.22的源地址 直接丢弃 …...

深度学习(14)--x.view()详解

在torch中&#xff0c;常用view()函数来改变tensor的形状 查询官方文档&#xff1a; torch.Tensor.view — PyTorch 2.2 documentationhttps://pytorch.org/docs/stable/generated/torch.Tensor.view.html#torch.Tensor.view示例 1.创建一个4x4的二维数组进行测试 x torch.…...

最新wordpress外贸主题

日用百货wordpress外贸主题 蓝色大气的wordpress外贸主题&#xff0c;适合做日用百货的外贸公司搭建跨境电商网站使用。 https://www.jianzhanpress.com/?p5248 添加剂wordpress外贸建站主题 橙色wordpress外贸建站主题&#xff0c;适合做食品添加剂或化工添加剂的外贸公司…...

Spring Cloud Gateway:使用RestController动态更新路由

相关类介绍 动态路由&#xff08;自己控制&#xff0c;非注册中心控制&#xff09;涉及两个很重要的Bean&#xff1a; RouteDefinitionWriter&#xff1a;用于添加、修改、删除路由规则。RouteDefinitionLocator&#xff1a;用于查询路由规则。 以及一个相关事件&#xff1a…...

用Python动态展示排序算法

文章目录 选择冒泡插入排序归并排序希尔排序 经常看到这种算法可视化的图片&#xff0c;但往往做不到和画图的人心灵相通&#xff0c;所以想自己画一下&#xff0c;本文主要实现归并排序和希尔排序&#xff0c;如果想实现其他算法可参考这篇 C语言实现各种排序算法[选择&#x…...

vscode代码快捷键

1、 log console.log()2、edf export default (first)>{ second } 或者 export default function(params)>{ }可以使用tab键切换修改项 3、ednf export default function first(second) {third}4、! 生成html模板 5、div#app <div id"app"></di…...

深入了解C++:形参、内联、重载、引用、const和指针、new和delete

形参带默认值的函数 1.给默认值的时候从右向左给。 2.定义出可以给形参默认值&#xff0c;声明也可以给形参默认值。 3.形参默认值只能出现一次。 4.参数调用的效率问题 #sum(10,20)对应了五条汇编指令 mov eax,dword ptr[ebp-8] push eax mov ecx dword ptr[ebp-4] push …...

Linux 目录结构结构

Linux 目录结构结构 概念 Linux 没有 C、D、E...盘符&#xff0c;只有一个目录树。通过挂载&#xff0c;将不同的磁盘挂载到目录树下&#xff0c;通过目录访问磁盘。 ‍ 不同目录的作用 目录存放内容/作用​/​根目录&#xff0c;目录树的起点&#xff0c;存放所有文件。​…...

C++基础入门:掌握核心概念(超全!)

C作为一门广泛使用的编程语言&#xff0c;以其高性能和灵活性在软件开发领域占据重要地位。无论是游戏开发、系统编程还是实时应用&#xff0c;C都是一个不可或缺的工具。本博客旨在为初学者提供C编程语言的核心概念&#xff0c;帮助你建立坚实的基础。 C关键字 C关键字是编程…...

Linux第47步_安装支持linux的第三方库和mkimage工具

安装支持linux的第三方库和mkimage工具&#xff0c;做好移植前的准备工作。 编译linux内核之前&#xff0c;需要先在 ubuntu上安装“lzop库”和“libssl-dev库”&#xff0c;否则内核编译会失败。 mkimage工具会在zImage镜像文件的前面添加0x40个字节的头部信息,就可以得到uI…...

数据工程工程师学习路线图

数据工程岗位要求 Skill Sets required: - Hands on experience enabling data via Adobe Analytics and/or Google Analytics - Understanding of how customer level data is captured and stitched with behavioural data - Experience working with Testing (QA) and D…...

MySQL主从同步与分库分表

分库分表...

百度PaddleOCR字符识别推理部署(C++)

1 环境 1.opencv&#xff08;https://sourceforge.net/projects/opencvlibrary/&#xff09; 2.cmake&#xff08;https://cmake.org/download/&#xff09; 3.vs2019&#xff08;(https://github.com/PaddlePaddle/PaddleOCR/tree/release/2.1) 4.paddleOCR项目-建议2.0(http…...

C++ Qt框架开发 | 基于Qt框架开发实时成绩显示排序系统(2)折线图显示

对上一篇的工作C学习笔记 | 基于Qt框架开发实时成绩显示排序系统1-CSDN博客继续优化&#xff0c;增加一个显示运动员每组成绩的折线图。 1&#xff09;在Qt Creator的项目文件&#xff08;.pro文件&#xff09;中添加对Qt Charts模块的支持&#xff1a; QT charts 2&#xf…...

Microsoft Excel 加载数据分析工具

Microsoft Excel 加载数据分析工具 1. 打开 Excel&#xff0c;文件 -> 选项2. 加载项 -> 转到…3. 分析工具库、分析工具库 - VBA4. 打开 Excel&#xff0c;数据 -> 数据分析References 1. 打开 Excel&#xff0c;文件 -> 选项 2. 加载项 -> 转到… ​​​ 3…...

Day32 贪心算法part02

买卖股票的最佳时机 太牛了我&#xff0c;随随便便双指针秒杀 md题解里面双指针都没用直接for循环秒杀 跳跃游戏 写成这样纯粹是没有看到第一次跳跃必须从第一个开始 class Solution:def canJump(self, nums: List[int]) -> bool:if len(nums) 1:return Truefor i in …...

3分钟带你了解Vue3的nextTick()

前言 Vue 实现响应式并不是数据发生变化之后 DOM 立即变化&#xff0c;而是按一定的策略进行 DOM 的更新。简单来说&#xff0c;Vue在修改数据后&#xff0c;视图不会立刻更新&#xff0c;而是等同一事件循环中的所有数据变化完成之后&#xff0c;再统一进行视图更新&#xff…...

数据库的使用方法

sqlite3 API&#xff1a; 头文件&#xff1a; #include <sqlite3.h> 编译时候要加上-lsqlite3 gcc a.c -lsqlite3 1&#xff09;sqlite3_open int sqlite3_open(const char *filename, /* Database filename (UTF-8) */ sqlite3 **ppDb /* OUT: SQLite db …...