硬核科普:什么是拓扑?

本文深入浅出地介绍了拓扑学的基础概念,通过橡皮泥几何的比喻,解释了为何甜甜圈与咖啡杯在拓扑学中被视为同一物体,以及如何通过拉伸和变形判断对象的拓扑等价性。文章探讨了拓扑空间、开集、同胚等核心概念,展示了拓扑学在数据分析和统计领域的应用潜力。

精彩马上开始!

“橡皮泥几何” 入门

我在大学学习拓扑时,总是不可避免地会遇到朋友和亲戚们的提问:

“拓扑到底是什么?”

这个问题很难回答,每次我都会给出略有不同的答案,但是答案总是不那么令人满意。如果你曾经在网上搜索过拓扑,你肯定会遇到将甜甜圈变成咖啡杯的动画,同样,我给出的答案也都与此相关:为什么甜甜圈跟咖啡杯在拓扑结构上是一样的,立方体和球体拓扑上也是一样的。但是这样的答案并不能真正解释真实的拓扑是什么,拓扑怎么应用以及其真正的价值是什么。

著名的咖啡杯和甜甜圈动画 | wiki

如果你有学到一般拓扑学的本科课程,可能会难以将所学的东西跟熟悉的甜甜圈和咖啡杯动画联系起来。这篇文章的目的是建立一般拓扑的基本概念,并说明拓扑跟熟悉的动画以及其他几何思想之间的联系。接下来,我们来了解,为什么将甜甜圈和咖啡杯视为一样的东西会是有用、有价值的。

总的来说,我发现很多人(包括我自己)都在努力尝试去理解:怎么才能将抽象的数学应用到实际的现实中。在了解拓扑的基本思想之后,我们可以重新思考真实世界,也许会产生出乎意料的结果。在此之前,我们将介绍拓扑的基本概念,这也是了解拓扑必不可少的定义。

拓扑空间

拓扑空间是具有最基本的结构的一组数学对象。数学中的结构通常意味着:数学对象之间的相加、相乘、距离或其他的概念。显然,这些结构适用于我们日常中遇到的数字。

但是,拓扑空间的结构比加法、乘法和距离的思想更加基本。事实上,这些数字所在的空间是拓扑空间的一个特定情况,也就是说,实数实际上是拓扑空间的一个特殊情况。

拓扑空间上的结构称为空间拓扑所有的拓扑都是数学对象的子集的集合,称为空间的“开集”。拓扑中包含的特定集合定义了空间的结构,这概念似乎很模糊和抽象,这是因为事实就是如此,这是数学中最抽象的结构形式。

当然,你不必完全理解此定义,只需记住拓扑及其内部的“开集”可以确定空间的结构。同样重要的是,使一个拓扑空间与另一个拓扑空间区分开的,是我们选择放入该空间拓扑中的集合。如果你感兴趣的话,以下是拓扑更加正式的定义。

拓扑空间定义

拓扑空间(X,τ)的数学对象集合是 X,空间拓扑是 τ,τ 包含 X 的一系列子集,满足下列条件:

1. X 和空集包含在 τ 中。

2. τ 中集合的任何并集也在 τ 中。

3. τ 中集合的任何有限交集也都在 τ 中。

那么,这怎么跟甜甜圈和咖啡杯联系起来呢?

通常,拓扑空间可以通过几何对象(例如球体)可视化:

图1 :球体

表示球体的拓扑空间是一些点的集合,如果将它们绘制在三维空间中,它们将构成一个球体以及一个拓扑。如前所述,拓扑定义了空间的结构,正是空间拓扑让这个球聚在一起不散开。我们可以将拓扑想象为“使所有点都不会掉落到地面上的事物”,它让球体保持单个物体的状态,而不仅仅是两个半球挤在一起。现在,设想一个如下图所示的拓扑空间:

图2:椭球

假设上面的球体(图1)是用橡皮泥制成的,那么我们可以轻松地将球体拉伸变成另一个对象椭球(图2)。三维对象能够执行此操作意味着这两个对象在拓扑上是相同(等价)的。这可能看起来很奇怪,但是仔细想一想,这两种形状有什么不同?虽然它们看起来不同,但是如果我们可以轻松地将它们挤压或拉伸实现形状的变化,它们是否真的是独特的?

这两个对象具有相同的拓扑,这意味着,即使这两个对象在几何形状上有所不同,但它们在拓扑上完全等价。我们可以将橡皮泥拉伸成可以想象的任何奇怪形状,但在拓扑结构世界中,所有这些形状都完全相同。也许你对拉伸的形状没有什么概念,但是关于如何拉伸橡皮泥的游戏有一些规则:

  1. 不允许在橡皮泥上打洞;

  2. 不允许将橡皮泥上的两点捏合在一起(我们没法将球形的橡皮泥做成甜甜圈的形状)。

如果我们在拉伸时违反了这些规则,那么这两个对象在拓扑上将不再等价。拓扑学家称这种不破坏既定规则的拉伸为同胚,这只是一种数学上精确地描述如何让橡皮泥的形状保持相同拓扑性质的方法。因此,如果我们可以得出两个拓扑空间之间的同胚性,则这些空间具有相同的拓扑,这就说到了咖啡杯和甜甜圈动画。

我们可以提供一个描述甜甜圈的拓扑空间,然后想象我们的甜甜圈是由橡皮泥制成的,然后在不破坏规则的情况下,将其拉伸到咖啡杯的形状。所以,是的,在拓扑结构上,咖啡杯和甜甜圈是同一件事。

图3:看起来不特别美味的甜甜圈

为什么球体不是甜甜圈?

现在,我们知道了如何判断两个对象在拓扑中的一致性,现在我们来看一下如何判断其在拓扑中的差异性。拓扑空间具有许多可以区分它们的不同属性。对于三维对象,例如球体和甜甜圈,我们可以用来区分二者的主要是它们具有的孔数。如果一个对象比另一个对象具有更多的孔,则二者在拓扑上是不同的。这是因为它们违反了我们先前建立的拉伸橡皮泥的规则。要造出一个孔,我们要么在橡皮泥上撕出一个洞,要么将橡皮泥拉伸成一个甜甜圈形状,然后将两端合并在一起。

图4:我们可以将橡皮泥球塑造成甜甜圈形状,但是在不违反规则的情况下,边线不能融合在一起。当我们将其弯曲成甜甜圈时,通心粉形状的两个圆形面仍然存在。

在拓扑上区分三维对象的另一种常用方法是,想象在三维对象上面行走。例如,在球体上行走。假设你从某个点开始,一直绕着球体上的一个大圆圈行走,当你再次到达同一点后,可以沿任一方向旋转90度,然后绕着另一个大圆圈走。在绕球的第二圈中,你将穿越第一条路径。无论你在球面上的哪一点上执行此操作,都会发生这种情况。

图5:具有两条相交路径的球体

在与球体拓扑等价的任何三维对象上也会发生这种现象。但是,在某些拓扑上与球体不等价的对象上,有方法可以做到这一点而不穿越第一条路径,你可以在甜甜圈上看到这个现象。

图6:如果我们从蓝色和绿色路径相交的地方开始,然后沿着绿色路径行走,这条路径跟我们已经走过的地方不相交。

对于拓扑等价的对象,他们的许多拓扑性质都是相同的;对于拓扑不等价的对象,这些拓扑性质则不一定相同。这些拓扑性质,就是用于确定两个对象拓扑等价与否的重要工具。

其他的拓扑对象

到目前为止,我们仅讨论了可以在3维中可视化的拓扑空间,但拓扑的一个优势是,它允许我们使用同样的方法轻松地描述4、5或更高维中存在的对象。

此类拓扑结构中经常出场的是克莱因瓶:

图7:三维空间中克莱因瓶的表示 | youtube:Numberphile

严格来说,我们实际上无法在三维空间中观察到真正的克莱因瓶,但是通过允许其自身交叉,我们可以对它的性质有所了解。在四维空间中,该对象实际上并不与自身交叉。很难想象的是,它会在第四维度弯曲以重新连接到自身。克莱因瓶看起来像有内外两侧,但是你可以从一个特定点沿一条连续的路径走,你将经过克莱因瓶的“外部”和“内部”,最后回到原始点,这说明克莱因瓶的3D表示在拓扑上是同一个面。因此,克莱因瓶没有容积。

但是,关于克莱因瓶上的路径的一个有趣的事情是,如果沿着上述路径行走,当你返回到原始位置时,你实际上将成为自己的镜像。这是与克莱因瓶在拓扑上等效(或同胚)的对象的拓扑属性。显然,克莱因瓶对球体或甜甜圈不是同胚的,因为无论我们在球体或甜甜圈上行走的方式如何,当我们回到起点时,我们都不会成为自己的镜像。如果对象具有成为自己镜像的这种属性,则将它们称为不可定向的。克莱因瓶不可定向,球形和甜甜圈可定向。另一个著名的不可定向表面是莫比乌斯带,这个很容易用纸条制作,网上也有很多教程。

当螃蟹在莫比乌斯带上行走并返回其原始位置时,它就是其自身的镜像。资料来源:Wikimedia Commons

尽管莫比乌斯带不可定向,但它在拓扑结构上不等同于克莱因瓶,而且其结构是一个整体。虽然可以通过将两个莫比乌斯条的边缘粘合在一起来构造克莱因瓶,但实际上在三维空间中这样做是不可能的(你可以尝试)。

用一张纸构造一个甜甜圈

研究在三维空间中难以可视化的对象(例如克莱因瓶)的拓扑的一种更实用的方法是考虑其粘合图粘合图通过拉伸和粘合2D形状的边缘的方式,来指导我们如何构造具有特定拓扑的对象

在考虑复杂形状的粘合图之前,首先考虑一个更简单形状的粘合图,甜甜圈:

图7:甜甜圈的粘贴图


我们假设图中的正方形是用橡皮泥制成的,然后想象一下拉伸正方形让对侧的边缘附着在一起或粘贴起来。当我们将这些边缘粘合在一起时,我们需要箭头指向同一方向。因此,我们将上图扩展如下:

图8:如何从其粘合图构造甜甜圈

下一个图类似于图 7,除了两个红色箭头现在处于相反的方向。这意味着我们需要扭曲对象,以便在将边缘胶合在一起之前,箭头指向同一方向:

图9 :更复杂的粘合图

上图粘合图中的第一步是拉伸正方形,使两条蓝线相交,然后我们构造一个圆柱体,就像构建甜甜圈的第一步一样。甜甜圈粘合的红色箭头指向相同的方向,而现在,这两个红色箭头则指向相反的方向。这意味着我们必须以某种方式扭转圆柱体的一端,以使箭头在将它们胶合在一起之前指向相同的方向。你可能会想到,这在物理上是不可能的。因此,由该粘合图产生的表面在物理上也是不可能的。但是实际上,这是我们已经见过的物理上不可能的表面,克莱因瓶

Source: Fouriest Series on tumblr

粘合图是查看对象是否可定向的简单方法。我们可以想象在粘合图上行走与在“吃豆人”中的原理类似,当吃豆人到达世界的一侧时,它可以从另一侧出来。如果我们想象吃豆人在粘合图上移动,当它进入一侧时,它将从同一颜色的另一侧冒出来,而箭头确定了它前进的方向。

假设吃豆人进入圆环粘合图的右侧,那么它将从左侧出现。这就是正常“吃豆人”世界的拓扑工作方式。

图10:吃豆人在圆环上行走

现在假设吃豆人进入了克莱因瓶粘合图的右侧,然后,吃豆人将在左侧出现,但上下颠倒了:

图11:吃豆人在克莱恩瓶上行走

由以上分析可知: 粘合图能使我们轻松考虑对象的某些拓扑属性,如果没有粘合图,这些属性将难以理解和利用。

拓扑为什么有用?

实际上,拓扑在统计领域中非常有用。统计学中一个新兴的研究领域是拓扑数据分析。有用的数据通常具有某种结构,这些结构具有某种规律或趋势,而数据分析本质上是揭示此结构的过程。在数据中寻找结构通常取决于我们如何看待数据,即:使用什么统计检验,将哪些变量与其他变量进行比较以及使用哪些可视化表示。

从拓扑结构中,我们知道看起来完全不同的事物实际上可以具有相同的结构。这个想法也可以应用于数据,因为即使在处理相同的数据,若看待数据的角度不同,它们看起来也可能完全不同。

在拓扑数据分析中,数据的结构将会进行拓扑处理。我们知道,拓扑属性是在不改变其拓扑性质的变换过程中保持不变的属性。因此,在对数据进行拓扑数据分析时,我们主要寻找在经过各种处理方式之后保持不变的属性,这个过程可以类比于像拉伸橡皮泥一样拉伸数据。通过这种方式,我们可以确定数据的真实结构,并且不再依赖数据的观察方式。

这只是所谓的“现实世界”中许多拓扑应用之一。其他拓扑应用程序还涉及看起来不同的事物实际上是否是相同的问题,这个问题在处理经由不同的人、不同方式表述的同样的信息中非常重要。具有不同的表示方式的几种情况有:分子结构、地理图、DNA结构和绳结等等。

虽然最初可能很难看清,但是拓扑是大多数数学领域的基础。确切定义拓扑的“使用方式”非常困难,因为它的存在在数学的工作方式中根深蒂固,以至于我们甚至都没有注意到我们正在使用它。直到最近,拓扑学才成为独立于其他数学领域的学科,不断涌现出新的研究成果和应用。

作者:Luke Cooper

翻译:Nuor

审校:xux

原文链接:

‍https://medium.com/cantors-paradise/what-is-topology-963ef4cc6365

我们是谁:

MatheMagician,中文“数学魔术师”,原指用数学设计魔术的魔术师和数学家。既取其用数学来变魔术的本义,也取像魔术一样玩数学的意思。文章内容涵盖互联网,计算机,统计,算法,NLP等前沿的数学及应用领域;也包括魔术思想,流程鉴等魔术内容;以及结合二者的数学魔术分享,还有一些思辨性的谈天说地的随笔。希望你能和我一起,既能感性思考又保持理性思维,享受人生乐趣。欢迎扫码关注和在文末或公众号留言与我交流!

扫描二维码

关注更多精彩

约瑟夫问题与魔术(一)——数学模型求解

每一个魔术,都应该是一场直播的微电影!

一次刨根问底的收获——从一道微积分题说开去

序列周期性与魔术(六)——魔术欣赏与解析续集

《猫和老鼠》里的魔术艺术(五)——一定要合理!


点击阅读原文,往期精彩不错过!
<think>我们正在讨论的是Verilog中的用户自定义原语(UDP),具体是一个名为`dffrsb_udp`的模块。但是,用户并没有提供这个UDP的具体定义。通常,UDP可以用来定义组合逻辑或时序逻辑的基本元件。从名称“dffrsb_udp”来看,它很可能是一个带有异步置位(Set)和复位(Reset)功能的D触发器(D Flip-Flop)。 ### 1. 用户自定义原语(UDP)概述 - **UDP定义位置**:UDP定义可以出现在模块(module)内部,但必须在模块的端口声明之前(即在`input`/`output`声明之前)[^1]。UDP也可以在模块外部定义(即全局定义)。 - **类型**:UDP可以定义组合逻辑或时序逻辑。时序逻辑的UDP中,输出必须声明为`reg`类型[^4]。 - **端口**: - 输出端口必须只有一个,并且位于端口列表的第一个。 - 输入端口可以有多个(最多10个)[^4]。 - 所有端口都是标量(即1位宽)[^4]。 ### 2. D触发器UDP的典型结构 一个常见的带有异步置位和复位的D触发器(通常称为DFFSR)的UDP定义可能如下: ```verilog primitive dffrsb_udp (q, d, clk, set, reset); output q; input d, clk, set, reset; reg q; // 真值表 table // 注意:顺序为 clk, set, reset, d : 当前状态 : 下一状态 // 异步置位(set)和复位(reset)优先级最高,低电平有效(假设) // 异步置位(set=0),无论时钟和复位如何,输出q置为1 ? 0 ? ? : ? : 1; // 异步复位(reset=0),无论时钟和置位如何,输出q置为0 ? ? 0 ? : ? : 0; // 同步部分:在时钟上升沿(0->1)传递数据 (01) 1 1 0 : ? : 0; // 时钟上升沿,d=0,输出变为0 (01) 1 1 1 : ? : 1; // 时钟上升沿,d=1,输出变为1 // 以下情况保持状态不变 ? 1 1 ? : ? : -; // 非时钟上升沿,或者置位/复位无效,则保持 (1?) 1 1 ? : ? : -; // 时钟稳定或下降沿,保持 (0?) 1 1 ? : ? : -; endtable endprimitive ``` - **说明**: - `dffrsb_udp`:原语名称。 - 端口:`q`(输出,必须在第一个),`d`(数据输入),`clk`(时钟),`set`(异步置位,通常低电平有效),`reset`(异步复位,通常低电平有效)。 - 真值表: - 异步置位(set=0)时,输出q立即变为1,与时钟和复位无关。 - 异步复位(reset=0)时,输出q立即变为0,与时钟和置位无关。 - 当异步控制无效(set=1且reset=1)时,在时钟上升沿(0->1)将输入d的值传给输出q。 - 其他情况(如非上升沿、异步控制信号无效时)输出保持不变(用`-`表示)。 ### 3. 功能总结 `dffrsb_udp`是一个用户自定义的D触发器原语,具有: - **异步置位(Set)**:当有效时(假设低电平有效),强制输出为1。 - **异步复位(Reset)**:当有效时(假设低电平有效),强制输出为0。 - **同步数据传递**:在时钟上升沿,将输入`d`的值传递给输出`q`。 - **优先级**:通常,异步置位和复位的优先级高于时钟触发(具体看设计,一般复位优先级最高,但本例中置位和复位同时有效时,由于真值表顺序,复位在置位之后定义,可能会被置位覆盖,所以需要注意顺序或明确优先级)。 > **注意**:具体行为取决于真值表的编写,包括信号的有效电平(高或低)和优先级。在实际使用中,需要根据设计规范确定。 ### 4. UDP的使用 定义UDP后,可以在模块中像使用内置门级原语一样实例化它。例如: ```verilog module my_dff( output reg q, input d, clk, set, reset ); // 实例化UDP dffrsb_udp inst_udp (q, d, clk, set, reset); endmodule ``` ### 注意事项 - UDP只能描述简单的逻辑,不支持多比特信号。 - UDP的定义不能包含行为级描述(如always块),只能通过真值表或状态表定义。 - 在综合时,UDP可能不被所有综合工具支持,因此使用前需确认工具链兼容性。 §§相关问题§§ 1. 如何确定UDP中异步置位和复位的优先级? 2. UDP与时序逻辑模块(如always块)相比有什么优势和劣势? 3. 能否在UDP中使用双向端口? 4. 如何为带异步控制的D触发器编写测试平台(Testbench)? </think> ### Verilog 中 `primitive dffrsb_udp` 的功能解析 `primitive dffrsb_udp` 是一个用户自定义原语(UDP),用于模拟**带异步复位(Reset)和异步置位(Set)的 D 触发器(D Flip-Flop)**。其功能是通过真值表(`table`)定义时序逻辑行为,具有以下核心特性: --- #### 1. **端口含义与功能** - **输出端口**: `q`:触发器的输出值(**必须声明为 `reg` 类型**,因时序逻辑要求存储状态)[^4]。 - **输入端口**(典型配置): - `d`:数据输入(Data) - `clk`:时钟信号(Clock) - `rst`:异步复位信号(Reset,低/高电平有效) - `set`:异步置位信号(Set,低/高电平有效) > 📌 **命名解释**: > `dffrsb_udp` = D Flip-Flop + Reset + Set + UDP(缩写清晰体现功能)。 --- #### 2. **真值表行为** 通过 `table` 定义逻辑行为(以低电平复位/置位为例): ```verilog primitive dffrsb_udp (q, d, clk, rst, set); output q; input d, clk, rst, set; reg q; // 输出必须为 reg table // 异步复位(rst=0):强制 q=0 ? ? 0 ? : ? : 0; // 任意输入下,rst=0 则 q=0 // 异步置位(set=0):强制 q=1 ? ? ? 0 : ? : 1; // 任意输入下,set=0 则 q=1 // 同步时钟触发:clk 上升沿锁存数据 d (01) ? 1 1 : ? : 1; // clk↑、rst=1、set=1:q = 1(d=1) (01) ? 1 1 : ? : 0; // clk↑、rst=1、set=1:q = 0(d=0) // 非触发/保持状态 ? * 1 1 : ? : -; // 非上升沿保持当前值("-" 表示不变) endtable endprimitive ``` **关键行为**: 1. **异步复位(Reset)优先**:若 `rst` 有效(如低电平),直接强制 `q=0`。 2. **异步置位(Set)次优先**:若 `set` 有效(如低电平),强制 `q=1`。 3. **时钟同步**:复位/置位无效时,`clk` 上升沿锁存输入 `d` 到输出 `q`。 4. **保持状态**:非时钟边沿或未定义输入时保持输出不变(`-`)。 --- #### 3. **硬件实现对应** - **物理电路**: 等效于下图结构(*示意图*): ```mermaid graph LR D[Data d] --> FF[D Flip-Flop] clk --> FF rst(Reset) --异步控制--> MUX1 set(Set) --异步控制--> MUX2 FF --> MUX2 --> q(Output q) MUX1 -->|复位路径| MUX2 ``` - 异步信号直接绕过时钟控制输出。 --- #### 4. **优势与典型场景** - **优势**: 1. **仿真效率**:UDP 在仿真器中直接映射到底层原语,速度快于行为级代码[^2]。 2. **门级建模**:适合 ASIC 标准单元库或 FPGA 硬核开发。 - **应用场景**: - 高可靠性设计(如复位/电源管理电路) - 时钟域交叉(CDC)的亚稳态处理 - 定制标准单元库开发[^1] > ⚠️ **限制**: > - UDP 最多 10 个输入、1 个输出,所有端口须为 1 位标量[^4]。 > - 不可调用其他模块或原语[^2]。 --- #### 5. **调用示例** 在模块内实例化(不可嵌入 `always` 块): ```verilog module top_module (output q, input d, clk, rst, set); // 在端口声明前定义 UDP(Verilog 规范要求)[^1] dffrsb_udp inst1 (.q(q), .d(d), .clk(clk), .rst(rst), .set(set)); endmodule ```
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值