“闭门造车”之多模态思路浅谈:自回归学习与生成

c8151d87cc3ebfd9b3c0525b20ed2b97.gif

©PaperWeekly 原创 · 作者 | 苏剑林

单位 | 科学空间

研究方向 | NLP、神经网络

这篇文章我们继续来闭门造车,分享一下笔者最近对多模态学习的一些新理解。

在前文《“闭门造车”之多模态思路浅谈:无损》中,我们强调了无损输入对于理想的多模型模态的重要性。如果这个观点成立,那么当前基于 VQ-VAE、VQ-GAN 等将图像离散化的主流思路就存在能力瓶颈,因为只需要简单计算一下信息熵就可以表明离散化必然会有严重的信息损失,所以更有前景或者说更长远的方案应该是输入连续型特征,比如直接将图像的原始像素特征 Patchify 后输入到模型中。

然而,连续型输入对于图像理解自然简单,但对图像生成来说则引入了额外的困难,因为非离散化无法直接套用文本的自回归框架,多少都要加入一些新内容如扩散,这就引出了本文的主题——如何进行多模态的自回归学习与生成。当然,非离散化只是表面的困难,更艰巨的部份还在后头。

ad787762c93505380c0627250d37a5fb.png

无损含义

首先我们再来明确一下无损的含义。无损并不是指整个计算过程中一丁点损失都不能有,这不现实,也不符合我们所理解的深度学习的要义——在 2015 年的文章《闲聊:神经网络与深度学习》[1] 我们就提到过,深度学习成功的关键是信息损失。所以,这里无损的含义很简单,单纯是希望作为模型的输入来说尽可能无损。

当前多模态模型的主流架构依然是 Transformer,很多工作都会先对图像进行“前处理”再输入到 Transformer 中,比如简单将图像 Pixels 分 Patch、通过 VAE 来提取特征或者通过 VQ 来离散化等,其共同特点是将图像从 的数组变成 (其中 )的数组,我们都可以称为广义的 “Patchify”。

不同的 Patchify 可能会有不同程度的信息损失,其中 VQ 的信息损失往往是最严重且最明确的,比如最近字节的 TiTok [2] 将 256*256 的图像压缩为 32 个 token,要理解它的信息损失都不用算信息熵,因为它的编码本只有 4096,意味着它顶多能存 张图片,我们知道汉字就不止 4096 个了,换句话说如果图上有 32 个汉字,那么所有排列组合就超出了这种编码方式能表达的上限。

如果图像在输入模型之前就有明显信息损失,那么必然会限制模型的图像理解能力,比如将 TiTok 的 32 个 Token 输入到模型中,那么它基本就没法做 OCR 任务了,而且 VQ 的这个瓶颈非常本质,即使改为 32*32 个 Token 也很难有明显的改善,除非 Token 的数量达到了原始 RGB 的 Pixels 数量级,但这样一来 VQ 的意义也就没有了。

所以,为了更好地适应各种图像理解任务,多模态模型理想的图像输入方式应该就是尽可能无损的连续型特征,由模型自己在计算过程中根据上下文决定要损失什么。

29f0e343e0559a71384710a3788b5f2b.png

自回归式

正如本文开头所说,以连续型特征输入对于图像理解来说其实是一个非常合理和自然的方式,只是对于图像的自回归(AutoRegressive,AR)生成来说会引入额外的困难。看到这里读者可能会有一个疑问:为什么图像非得要做自回归?图像不是有扩散模型这样的更好用的生成方式了吗?

首先,我们知道,“自回归模型 + Teacher Forcing 训练”本身就是一种非常普适的学习途径,是“手把手教学”的典型体现,所以它潜力是足够的;其次,扩散模型这个例子,更加说明了自回归在图像生成中的必要性。

以 DDPM 为例,它实质就是一个自回归模型,在《生成扩散模型漫谈:DDPM = 自回归式VAE》我们就将其冠以自回归之名,它将单个图像解构为序列 ,然后去建模 ,训练方式本质上也是 Teacher Forcing(所以也有 Exposure Bias 问题),可以说 DDPM 不仅是自回归,而且还只是自回归中最简单的 2-gram 模型。

事实上,从早期的 PixelRNN [3]、PixelCNN [4]、NVAE [5] 等工作,到如今流行的扩散模型以及将图像 VQ 之后当文本那样训练语言模型,它们传递出来的信号更多的是——对于图像来说,问题并不是该不该做自回归,而是以何种方式来更好地去做自回归。它的作用不仅是为多模态模型赋予图像生成能力,而且还是一个重要的无监督学习途径。

笔者的偶像 Feynman 说过一句著名的话 “What I cannot create, I do not understand”,这句话放到大模型也是成立的,也就是说“不会生成就不会理解”。当然,这句话看上去有点武断,因为通过有监督学习各种图文数据对似乎也能获得足够的图像理解能力。

然而,单纯通过有监督的方式去学习图像理解,一方面覆盖面可能有限,另一方面也受限于人的理解水平,所以我们需要无监督的生成式预训练来获得更充分的图像理解能力,这跟文本的 “Pretrain + SFT” 的 Pipeline 是一致的。

38349563ac84c758b829f52822dcb4ce.png

平方误差

可能有部份读者觉得,将图像分 Patch 排序后,不也就可以跟文本一样预测下一个 Patch 吗?就算输入格式不离散化而是改为连续特征,那也只需要把交叉熵损失换成平方误差就行了?看上去图像的自回归学习也没有什么困难?思路上确实如此,但事实上这里边提到的两个关键地方——“分 Patch 排序“损失函数”——都是难以解决的问题。

这一节我们先来看损失函数问题。假设图像已经按某种方式分 Patch 排序好,那么图像就变成了 Patch 的一维序列,自回归学习也确实是对下一个 Patch 的预测,如下图所示:

eec9acf9a4163a4ef473126acc75c758.png

▲ 图像自回归学习的最朴素想法是用平方误差预测下一个 Patch

然而,这里的损失函数却没法简单地用平方误差(MSE,或者等价地,欧氏距离,L2 距离),这是因为平方误差背后的关于分布的假设是高斯分布:

b918e75b9b02bc394d2e2dd39335ff94.png

即高斯分布 的负对数似然正好是平方误差(其中 是常数),这意味着用平方误差的话对 的假设为 ,但我们仔细想想就会发现,这个假设跟真实情况还是相距甚远的,因为如果它成立,那么通过 就可以完成 的采样,其实 是标准高斯分布的噪声,那么 必然会有很多噪点,而真实情况显然未必如此。

可能又有读者反驳:为什么非得要从概率似然的角度来理解呢?我就纯粹将它理解为一个回归拟合问题不行吗?可能真的不大行。从概率角度理解主要有两方面的考虑:

第一,生成建模最终都要面临采样,写出概率分布才能构建采样方式;

第二,单纯从回归的角度来看,我们也需要论证平方误差的合理性,因为我们还有很多其他损失可以用,比如 L1 距离(MAE)、Hinge Loss 等等,这些损失并不相互等价,也不尽合理(事实上,这些损失都不合理,因为它们都是从纯数学角度定义出来的度量,跟人类视觉认知并不完全吻合)。

4c06e6fcc2677fcd4c28ac61b8d88d37.png

噪声之奇

由于是输入的图片特征本质决定了平方误差的不合理性,所以解决这个问题的唯一思路就是修改图片的输入格式,使得它相应的条件分布更符合高斯分布。目前看来,有两个具体的方案可以参考。

第一个方案是通过预训练的 Encoder 来编码图片,其中训练 Encoder 时通常会加入 VAE 的 KL 散度等正则项来缩小方差,说得更直观一点,就是将特征都压缩在一个球附近(参考《从几何视角来理解VAE的尝试》[6]),用这些特征作为图像的输入,会使得 是高斯分布的假设更加合理一些,所以我们可以用平方误差来自回归训练,训练完之后,我们还需要另外训一个 Decoder,来将采样出来的图片特征解码为一张图片。这大体上就是 Emu2 [7] 所采用的方案,缺点是 Pipeline 看起来太长,不够端到端。

第二个方案可能会出乎很多人意料,那就是加噪,这是笔者闭门造车的想法。刚才我们说如果 真的是高斯分布,那么直观来看 应该有很多噪点才对,但事实上没有。那为了满足这个条件,我们自己加一些噪声不就行了?加了噪声也不一定能让 变成高斯分布,但可以让它更接近,尤其是当我们渐进地加噪声的时候,如下图所示

a443c0260b36ff450e70c465234ff557.png

▲ 通过加噪拓展每个 Patch,让平方误差成为可行的损失函数

了解扩散模型的读者不难想到,通过加噪来构建渐变序列,然后以平方误差为损失来训练递归去噪模型,这不就是扩散模型吗?没错,扩散模型的核心思想正是“通过渐进式加噪让平方误差成为合理的损失函数”,而上述方案也是借用了这一思想。

当然,跟常规扩散模型的不同之处也是很明显的,比如扩散模型是对整张图片加噪,这里是对 Patch 加噪,扩散模型是建模 ,这里是建模 ,等等。从最终形式上来看,这里提出的是一种结合扩散模型来进行图像的自回归学习的方案。

cb4e5409fc1502809b49fc868e91b8eb.png

效率问题

通过加噪来延长序列,使得朴素的平方误差可用,从而让图像的自回归学习跟我们开始构思的方案基本一致(就只是输入多了一步加噪),这无疑是一个非常让人舒适的结果。然而,事情并没有那么乐观,这个方案至少有两大问题,这两个问题也可以概括为同一个词——效率。

第一,是学习效率问题。这个问题我们在第一篇介绍扩散模型的文章《生成扩散模型漫谈:DDPM = 拆楼 + 建楼》就已经讨论过了,大致意思就是这种 时刻的加噪图预测 时刻的加噪图的训练目标,需要对噪声进行双重采样,这会导致更大的训练方差,因此需要更多的训练步数才能把这个方差降下来,而经过一系列降方差技巧后,我们发现更高效的方式是直接预测原图(或者等价地,预测它与原图的差):

04016bca891134f1ac1507f790ed1d68.png

▲ 相比预测下一步噪声图,直接预测原图效率更高

可能有读者不能理解,刚刚不才说原图没有噪点不符合高斯分布,不能用平方误差为损失吗?这个问题还真不大容易从直观上来解释,我们可以理解为这是高斯分布的一个巧合,这时候平方误差还是可以用的,更标准的解释可以参考《生成扩散模型漫谈:DDPM = 贝叶斯 + 去噪》、《生成扩散模型漫谈:DDIM = 高观点DDPM》这两篇。

第二,是计算效率问题。这个其实很好理解,假如每个 Patch 通过加噪变成 T 个 Patch,那么序列长度就变为原来的 T 倍,这样一来训练成本和推理成本都会显著增加。此外,从理论上来说,加噪的 Patch 对图像理解并无实质帮助,只保留没加噪的那个干净 Patch 原则上也能达到同样的效果,换句话说,这种方案对于图像理解来说存在大量冗余的输入和计算量。

解决这个问题同样有两个思路,下面我们逐一介绍。

6777a748aeaef2753ca69ebd401dc38f.png

分离扩散 

如果限定必须在单个 Transformer 内解决的话,我们可以考虑给 Attention 加 Mask,这又包括两部分:1)扩散模型的理论和实践告诉我们,要预测 的话只用 就够了,可以忽略更早的输入,这意味同一个 Patch 的不同加噪结果之间不需要相互 Attend;2)出于减少冗余的考虑,对于不同 Patch 之间的预测以及后面文本 Token 的预测,我们只需要 Attend 到没加噪的 Patch。这就形成了大致如下的 Attention Mask:

ad8d32c5927a3dd2e24e101865beca54.png

▲ 出于简化模型和去冗余的考虑所设计的 Attention Mask

由于这种 Attention Mask 具有固定的 Sparse Pattern,所以它有很大的提速空间,并且由于带噪的 Patch 的注意力是独立的,因此我们训练时也不必一次性把 T−1 个带噪 Patch 都算进去,每次采样一部份计算就行。当然,这顶多只算一个雏形,实践中还有一些细节需要仔细斟酌一下,比如加噪的 Patch 之间基本没有关联,那么它们的位置编码需要单独设计一下,等等,这里就不展开讨论了。

如果允许两个不同的模型串联(但仍然可以端到端训练),那么我们还可以把扩散模型单独分离出来,Transformer 只负责处理没有噪声的 Patch,Transformer 的输出则作为扩散模型的条件,如下图所示:

13037f18657e39527c75fe10e06e7a1d.png

▲ 将扩散模型分离出来,Transformer 的输出作为扩散的输入条件

这大体上就是 Kaiming 的新工作《Autoregressive Image Generation without Vector Quantization》[8] 所提的方案,但它更早在《Denoising Autoregressive Representation Learning》[9] 就已经被提出,其好处是让 Transformer 部份更加纯粹和优雅,同时也可以起到节省计算量的作用,这是因为 1)单独分离出来的扩散模型可以做得更小一些;2)扩散模型部份我们可以按照常规的训练策略每次只采样一个噪声步计算。

从损失函数的角度来看,它就是利用了一个额外的扩散模型来作为预测下一个 Patch 的损失,从而解决平方误差的缺点。

60a88164646f00571e111a5cb1f613ad.png

生成方向

前面我们提到图像的自回归学习的两个关键之处分别是“分 Patch 排序”和“损失函数”,刚才我们花了四个小节勉强把损失函数这一块稍微捋顺了一下,但这只能算是刚刚摸到了门槛。然而,接下来我们将会发现一个更让人悲观的结果——对于“分 Patch 排序”这个问题,我们连门槛都很难摸到。

从最终目标来看,“分 Patch 排序”是为了给自回归学习制定一个生成序列和方向,它分为“分 Patch” 和“排序”两步。“分 Patch” 我们也称 “Patchify”,狭义的 Patchify 就是对像素数组的简单变形和转置,即将 的数组先变形为 ,然后转置为 ,最后变形为 。

但广义来说,Patchify 可以泛指一切将图像从 的数组变成 (其中 )的数组的方案,比如 Stable Diffusion 的 Encoder 将图像编码为 Latent、各种 VQ-Tokenizer 将图像变成离散的 ID,这些都算是广义的 Patchify。

“排序”就比较好理解了,我们知道图像有“长”和“宽”两个方向(维度),大部份 Patchify 方法的输出特征依然保留了这个二维性质,而自回归生成则是单向的,所以需要指定一个生成顺序。常见的顺序比如 1)从左往右再从上往下;2)从中心到四周螺旋;3)从左上角出发走 “Z” 字等等,这些排序设计由来已久,它们可以追溯到第一代图像自回归模型——直接在图像 Pixels 上做的自回归模型,即前面提到的 PixelRNN / PixelCNN 等。

98c10df820bab444c5cba8dddf5f51ab.png

▲ 朴素的 Patchify 和两种不同的排序方式

总的来说,“分 Patch 排序”是将图像解构为一个可供自回归学习的一维序列的过程,更通俗点就是将图像从二维序列转成一维序列,所以从最最广义的角度来讲,扩散模型来构建的不同噪声强度的带噪图片序列,以及《Visual Autoregressive Modeling: Scalable Image Generation via Next-Scale Prediction》[10] 多个 scale 构成的序列,都可以归入此列。

所以,现在我们已经提到了多种解构图像的方案,那么很自然的问题就是:哪个方案更好?判断依据是什么呢?

e2ee8ed05fa73e856d2182c4f4f07e0d.png

世界模型

要回答这个问题,我们首先要搞清楚,图像生成或者说视觉生成的本质难度是什么。在《“闭门造车”之多模态思路浅谈:无损》中,我们简单提到图像生成的困难在于连续型概率建模的困难,但实际上这是一个非常表面的判断,如果仅仅是这样的话,那么情况就乐观得多了,因为我们已经发展了不少诸如扩散模型的连续型生成模型,但实际上其中的困难比我们想象的更为深远...

我们所说的图像,大体上可以分为人类创造的图片以及相机拍摄的照片两种,在相机、手机普及之后,互联网上的图像实际上已经以照片为主,所以图像生成基本上也等价于照片生成。照片是什么呢?它是光的记录,是三维世界的光在二维平面的投影。那光又是什么呢?光是电磁波,电磁波是麦克斯韦方程组(Maxwell's equations)[11] 的解!

从这个思考中我们发现一个不可否认的事实:一张真实的自然照片,它本质上就是麦克斯韦方程组的一个解,这也就意味着,完美的图像生成不可避免地要触碰到物理定律——众多理论物理学家孜孜不倦地追求的世界本源!

无独有偶,在 Sora 出现之后,我们经常会用“是否符合真实世界的物理规律”来评价模型生成的视频质量,实际上看似更加简单图片生成,同样可以有“符合物理规律”这个评价维度,比如图片上的光影分布规律等,只不过到了视频这里,在光学(电磁学)的基础上多了一个动力学。

沿着这个思维链头脑风暴下去,会越来越让人觉得震撼甚至惊悚,因为这等价于说完美的视觉生成模型实际上就是在数值模拟各种物理定律,或者更夸张地说,它实际在模拟整个世界、整个宇宙的演化,它本质上就是一个世界模型。这已经不是地狱级难度可以形容的了,这简直就是创世级难度。

可能有读者质疑:麦克斯韦方程组是难,但不也被人类发现了?我们还发现了更多更难的物理规律,比如量子力学、广义相对论等等,并且还在不断逼近终极定律(大统一理论),所以这件事情的难度似乎没有那么高?

不,大家不要混淆了,即便我们真的能够发现完全正确的物理定律,那跟有能力“用这些定律去数值模拟”是两回事。比如我们能手写出一个方程,但未必能通过手算去求解它,所以我们能发现物理规律,不代表我们能利用这些物理规律去推演或者模拟真实世界,更具体一点,我们现在能在这里说照片的本质就是麦克斯韦方程组的一个解,但没有谁能够手绘一张照片出来。

(注:以上的一系列思考,起源于“图像本质是麦克斯韦方程组的一个解”,这是在一次技术交流中我的 leader 周昕宇分享给我的,当我第一次听到这个看上去荒谬但事实上不得不接受的观点时,我内心是错愕且震撼的,霎时间有种明悟了多模态模型的本质困难的感觉。)

18cfed57c2bcab74de7fc1625c091119.png

人价值观

总的来说,这个头脑风暴想要表达的观点就是,一个完美的视觉生成模型,它是一个真正意义上的世界模型,它的难度可谓是创世级别的。那么我们想要创世吗?我们有能力创世吗?

笔者认为在可以想象的时间内,答案都是否定的,毕竟那意味着要以人力跟全宇宙对抗的感觉了。所以这里的关键就是放弃“完美”这个概念,就好比人不能手绘出一张照片,但这依然不影响人作画,也不影响人通过手绘的方式来传递信息。又比如说我们评价模型生成的视频是否符合物理规律,并非真的是测量了视频的轨迹然后代入物理公式来判断的,而单纯是肉眼目测加上我们对物理规律的直观感知。

说白了,可以有损,但对人的价值观无损就行了。那这跟前面说的“分 Patch 排序”又有什么关系呢?我们一开始就说了,自回归学习不单是要为模型赋予生成能力,同时也是作为一种无监督学习途径,来提高模型的理解能力(不会生成就不会理解)。如果我们有一个真正无限拟合能力(创世能力)的模型,那么所有的“分 Patch 排序”都是等价的,因为精确的联合分布不依赖于随机变量的分解方式。但很遗憾我们没有,那么我们只能有所取舍。

注意,我们希望通过学习生成来促进理解,这里的“理解”必然是要对齐人的视觉理解的,这是我们训练 AI 的目的。然而,前面列举出来的一些“分 Patch 排序”方式,没有一种是符合人的视觉理解方式的。

更直接地说,人对图片的理解并不是从左往右或者从上往下,也不是从中间到四周还是走 “Z” 字,甚至说人理解图像都不是按照 Patch 为单位的,当然也不是 Diffusion 那样逐渐加噪的方式。

如果我们用已有的各种“分 Patch 排序”方案去做自回归学习,确实有机会赋予模型在一定范围内的视觉生成能力,但由于这些图片解构方式本质上都不符合人的视觉理解模式,那么很难认为这种自回归学习可以促进模型的视觉理解能力——更准确地说,是很难促进模型模仿人视觉理解的能力。

造成这个困难的主要原因,是因为图像它是一个“结果”,并不包含“过程”。就拿人类创作的图像来说,不管是手绘的还是 PS 的,其过程都是一步一步操作的,但最终呈现出来的是一张掩盖了它创作过程的图像。

这跟文字不一样,我们虽然不知道作家是怎么构思出这段文字的,但我们知道大部份人都是从左往右写字的,所以文字本身就已经包含了它的创作(书写)过程,但如果是一幅画呢?看了一幅画,我们知道画家先画哪一块、哪一笔吗?显然不行,这也是为什么大部份人都会写字但无法临摹一幅画。更深一步想,这可以理解为人类似乎更擅长沿着时间维度模仿,而不擅长沿着空间维度,因为时间维度只有一个,空间维度却有三个,后者自由度太大。

目前看来,就只有一个非常“妥协”的方法来解决这个问题,就是用尽可能多的、符合人类价值观的图文数据(当然,图像的其他有价值的监督信号也可以),去有监督地训练一个“分 Patch 排序”模型。注意跟常见的 Vision Encoder 不同,这个模型要直接输出一维序列,而不是保留图片的二维性,这样就免去了事后排序这一步。

模型的设计我们可以参考 TiTok [2](这是我们第三次提到 TiTok了),它本质上是利用 Cross Attention 将二维序列转一维序列,除此之外用 Q-Former [12] 也能实现类似的效果。总之,模型设计上不会有太多难度,核心工作变成了图文对的数据工程了。

但这样一来,模型能走多远就不好说了,因为我们本希望通过自回归学习来促进模型的理解能力,但现在自回归学习又依赖于一个通过理解任务训练出来的 Encoder,理想情况下这两个模型会相互促进、共同进化,但不理想的情况下模型能力就受限于训练 Encoder 的有监督数据的数量和质量,无法形成真正的无监督学习了。

20d9896c5c47c45fa1617eb3d43f9de3.png

文章小结

这篇文章继续“闭门造车”了一些有关多模态学习的思路,主要围绕视觉的自回归学习进行展开,大体内容是:

1. 自回归学习既为模型赋予了生成能力,同时也是通过生成来促进理解能力的无监督学习途径;

2. 对于图像来说,问题不在于要不要做自回归,而是以何种方式才能更好地做自回归;

3. 将图像以连续型特征的方式输入时,它的自回归学习有两大难题:分 Patch 排序和损失函数;

4. 损失函数不能简单用平方误差,而是可以考虑后面接一个小型的扩散模型来预测下一个 Patch;

5. “分 Patch 排序”是图像自回归学习的根本难题,它的选择关系到自回归学习能否真正促进理解;

6. 完美的图像/视觉生成,不可避免要跟物理规律建立联系,从而构成“世界模型”;

7. 但世界模型难以实现,所以选择跟人类价值观相符的“分 Patch 排序”方式尤为重要;

8. 最后,看上去只能“妥协”地通过有监督学习来获得一个对齐人类价值观的“分 Patch 排序”模型。

这里边可能有不少“暴论”和“谬论”,请读者自行甄别和海涵。将这些思考写下来的主要目的,是为了未来的某一天再回过头来看看,自己当初的想法有几分可行,又有几分可笑。

outside_default.png

参考文献

outside_default.png

[1] https://kexue.fm/archives/3331

[2] https://papers.cool/arxiv/2406.07550

[3] https://papers.cool/arxiv/1601.06759

[4] https://papers.cool/arxiv/1606.05328

[5] https://kexue.fm/archives/7574

[6] https://kexue.fm/archives/7725

[7] https://papers.cool/arxiv/2312.13286

[8] https://papers.cool/arxiv/2406.11838

[9] https://papers.cool/arxiv/2403.05196

[10] https://papers.cool/arxiv/2404.02905

[11] https://en.wikipedia.org/wiki/Maxwell%27s_equations

[12] https://papers.cool/arxiv/2301.12597

更多阅读

5fed8d1073f735abd400e4f0ac765661.png

3ad591c4c6d01221a3815911816ce518.png

cd699392482e28f4cad1b5b35433e621.png

c6b208e8bfeaf23c499c68e181a637b5.gif

#投 稿 通 道#

 让你的文字被更多人看到 

如何才能让更多的优质内容以更短路径到达读者群体,缩短读者寻找优质内容的成本呢?答案就是:你不认识的人。

总有一些你不认识的人,知道你想知道的东西。PaperWeekly 或许可以成为一座桥梁,促使不同背景、不同方向的学者和学术灵感相互碰撞,迸发出更多的可能性。 

PaperWeekly 鼓励高校实验室或个人,在我们的平台上分享各类优质内容,可以是最新论文解读,也可以是学术热点剖析科研心得竞赛经验讲解等。我们的目的只有一个,让知识真正流动起来。

📝 稿件基本要求:

• 文章确系个人原创作品,未曾在公开渠道发表,如为其他平台已发表或待发表的文章,请明确标注 

• 稿件建议以 markdown 格式撰写,文中配图以附件形式发送,要求图片清晰,无版权问题

• PaperWeekly 尊重原作者署名权,并将为每篇被采纳的原创首发稿件,提供业内具有竞争力稿酬,具体依据文章阅读量和文章质量阶梯制结算

📬 投稿通道:

• 投稿邮箱:hr@paperweekly.site 

• 来稿请备注即时联系方式(微信),以便我们在稿件选用的第一时间联系作者

• 您也可以直接添加小编微信(pwbot02)快速投稿,备注:姓名-投稿

4f7c9bb3e00dcfc12daf7a24d71e4f30.png

△长按添加PaperWeekly小编

🔍

现在,在「知乎」也能找到我们了

进入知乎首页搜索「PaperWeekly」

点击「关注」订阅我们的专栏吧

·

·

·

7e322a42ff2a6a3f58d5cb00cf55b0d9.jpeg

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Qt中实现让静态图片动起来,创建动画效果

在现代应用程序开发中,动画效果是提升用户体验的重要元素之一。Qt作为一个强大的跨平台应用程序框架,提供了丰富的工具和库来创建各种动画效果。本文将介绍如何在Qt中使用静态图片创建动画效果。 实现方法一 使用QTimer和QPixmap 1.准备图片资源&#…

Diffusion model笔记

![在这里插入图片描述](https://i-blog.csdnimg.cn/direct/f5ec0915d48e4e17bf158b70296cc8d8.png stable diffusion

谷粒商城实战笔记-27-分布式组件-SpringCloud-Gateway-创建测试API网关

本节的主要内容是创建网关模块,将网关注册到Nacos,并配置路由进行测试。 一,创建网关模块 右键工程New->Module,创建新模块,模块名称 gulimall-gateway。 填充各种信息。 选中Gateway依赖。 点击Create创建模块。…

普中51单片机:定时器与计数器详解及应用(七)

文章目录 引言定时器工作原理TMOD定时器/计数器工作模式寄存器定时器工作模式模式0(13位定时器/计数器)模式1(16位定时器/计数器)模式2(8位自动重装模式)模式3(两个8位计数器) 定时器配置流程代码演示——LED1间隔1秒闪烁代码演示——按键1控制LED流水灯状态代码演示——LCD160…

企业数据治理做完了,如何让业务部门用起来

引言:企业数据治理完成后,确保业务部门能够充分利用这些数据并融入日常运营中,是实现数据价值最大化的关键步骤。以下是一些策略和建议,帮助推动业务部门使用数据治理成果: 一、管理层面推广 高层应用示范&#xff1…

【漏洞复现】方正全媒体采编系统——binary.do——SQL注入

声明:本文档或演示材料仅供教育和教学目的使用,任何个人或组织使用本文档中的信息进行非法活动,均与本文档的作者或发布者无关。 文章目录 漏洞描述漏洞复现测试工具 漏洞描述 方正全媒体采编系统(FZMediaEditor)是一…

网络安全第一次作业

需求 前置工作 给设备配好ip地址,并且在总公司处配置vlan 1, 先建立多个安全区域 接着新建两个策略 :办公区访问dmz区域策略,生产区访问dmz区域策略 2 , 不做配置即可,生产区本不允许访问互联网 3, 新…

学习大数据DAY14 PLSQL基础语法3

目录 二重循环 三种循环随便嵌套 exit continue return 作业 数据提取 游标 隐式游标 显示游标 动态游标 游标使用流程 游标属性 游标配合循环使用示例 作业2 参数游标 current of 语句 作业3 PLSQL基础语法(三) 二重循环 三种循环随便嵌…

LangChain框架详解

LangChain框架详解 LangChain是一个基于语言模型开发应用程序的强大框架,旨在帮助开发人员简化与大模型交互、数据检索以及将不同功能模块串联起来以完成复杂任务的过程。它提供了一套丰富的工具、组件和接口,使开发人员能够轻松构建上下文感知和具备逻…

Qt:19.浮动窗口/子窗口(子窗口介绍、代码方式创建子窗口、设置子窗口标题、为子窗口添加控件、设置子窗口停靠位置)

目录 1.子窗口介绍: 2.代码方式创建子窗口: 3.设置子窗口标题: 4.为子窗口添加控件: 5.设置子窗口停靠位置。 1.子窗口介绍: 在 Qt 中,可以创建和管理子窗口(子窗口体)以实现多窗…

线程安全(二)synchronized 的底层实现原理、锁升级

目录 一、基础使用1.1 不加锁的代码实现1.2 加锁的代码实现二、实现原理2.1 synchronized 简介2.2 对象监控器(Monitor)2.3 加锁过程第一步:判断 Owner 指向第二步:进入 EntryList 阻塞第三步:主动进入 WaitSet 等待三、锁升级3.1 对象的内存结构3.2 Mark Word 对象头3.3 …

python的简单爬取

需要的第三方模块 requests winr打开命令行输入cmd 简单爬取的基本格式(爬取百度logo为例) import requests url"http://www.baidu.com/img/PCtm_d9c8750bed0b3c7d089fa7d55720d6cf.png" resprequests.get(url)#回应 #保存到本地 with open(&…

地址翻译过程(TLB-->页表-->Cache-->主存-->外存)

目录 1.地址结构 2.查找快表或页表:从虚拟地址--->物理地址 3.通过物理地址访问数据 设某系统满足以下条件: •有一个TLB与一个data Cache •存储器以字节为编址单位 •虚拟地址 14位 •物理地址 12位 •页面大小为 64B •TLB 为四路组相联&#x…

嵌入式工程师从0开始,到底该学什么,怎么学?

作为嵌入式工程师,从零开始学习需要掌握以下几个关键方面。我收集归类了一份嵌入式学习包,对于新手而言简直不要太棒,里面包括了新手各个时期的学习方向编程教学、问题视频讲解、毕设800套和语言类教学,敲个22就可以免费获得。 基…

【高中数学/指数函数、对数函数、正弦函数】求 y=2^x+x,y=log2_x+x,y=2*sinX+x 的零点位置大小关系

【问题】 已知函数f(x)2^xx,g(x)log2_xx,h(x)2*sinXx 的零点分别是a,b,c,则a、b、c的大小顺序是? 【解答】 粗览三个函数,h(x)2*sinXx的零点是最好解决的,明显x0时h(x)0,因此c在原点的位置; 对于f(x)2^xx&#xff…

【C++BFS】690. 员工的重要性

本文涉及知识点 CBFS算法 LeetCode690. 员工的重要性 你有一个保存员工信息的数据结构,它包含了员工唯一的 id ,重要度和直系下属的 id 。 给定一个员工数组 employees,其中: employees[i].id 是第 i 个员工的 ID。 employees[…

怎样在 C 语言中实现堆排序?

🍅关注博主🎗️ 带你畅游技术世界,不错过每一次成长机会! 📙C 语言百万年薪修炼课程 【https://dwz.mosong.cc/cyyjc】通俗易懂,深入浅出,匠心打磨,死磕细节,6年迭代&…

人类大脑的计算与机器的类脑计算

人类大脑的计算基本原理涉及到神经元的基本工作方式、神经网络的结构和连接模式、信息传递的方式、学习和记忆的机制等多个层面的复杂互动,这些原理的深入理解不仅有助于神经科学的发展,还为人工智能领域的发展提供了重要的启示和指导。人类大脑计算基本…

按下快门前的算法——对焦

对焦算法可以分为测距式,相位式,反差式。 其中测距式是通过激光,(TOF,Time of Flight)等主动式地得知物距,然后对焦。更常用的是后两者。 反差式CDAF(Contrast Detection Auto Foc…

Lingo学习(二)——线性规划基础、矩阵工厂

一、线性规划基础 (一)方法 ① 一个线性规划中只含一个目标函数。(两个以上是多目标线性规划,Lingo无法直接解) ② 求目标函数的最大值或最小值分别用max …或min …来表示。 ③ 以!开头,以;结束的语句是注释语句; ④ 线性规划和非线性规划的本质…