算法设计与分析 实验六 最大流解决论文评审问题_最大流 论文评审-程序员宅基地

技术标签: 算法  c++  算法设计与分析  数据结构  

一、实验目的与要求

1、实验目的:

(1)掌握最大流算法思想。
(2)学会用最大流算法求解应用问题。

2、实验亮点:

(1)正确构建了流网络,并详细分析了流网络的结果
(2)给出了流网络与问题解的关系
(3)使用多种方法正确计算了给定网络的最大流
(4)对多种算法实现过程中必要定理进行了严谨的证明

二、实验内容与方法

使用最大流解决论文评审问题:
(1)有m篇论文和n个评审,每篇论文需要安排a个评审,每个评审最多评b篇论文。请设计一个论文分配方案。
(2)要求应用最大流解决上述问题,画出m=10,n=3的流网络图并解释说明流网络图与论文评审问题的关系。
(3)编程实现所设计算法,计算a和b取不同值情况下的分配方案,如果没有可行方案则输出无解。

三、实验步骤与过程

(一)设计流网络

要想利用网络流解决问题,第一步当然是构建流网络。为了让流网络结构更加清晰,我采用了层次的概念对流网络进行构建。下图为构建出的网络流结果,其中,省略了一些重复的节点。
在这里插入图片描述

根据题意,可以构建出如上流网络。其中,流网络共分四层。第一层只有源点,第四层只有汇点。中间第二层表示各个评审,第三层表示各个待评审的论文。
源点→评审: 源点分别指向各个评审节点且容量都为每个评审的最大评审论文数。由于需要对各个论文进行评审,所以源点与每个评审间存在有向边。又因为每个评审最多可以评审b篇论文,因此,从源点到评审节点的最大流量为b。

评审→论文: 对于每个已经分配的评审,评审需要评阅论文,因此存在由评审到论文的有向边。又因为对于每个评审,其评阅论文的状态只有0或1即表示未评阅或已评阅。因此从评审到论文的有向边的最大流量为1。

论文→汇点: 完成论文的评阅后将流网络汇入汇点即可。又因为,每个论文至少由a名评审进行评阅,则从论文节点到汇点有最大容量为a的有向边。当 d o c 1 doc_1 doc1到汇点的容量为x时,表示论文 d o c 1 doc_1 doc1被x个评审评阅了。

下面以 m = 10 , n = 3 m=10,n=3 m=10,n=3(10篇论文,3位评审)时构建流网络为例,展示构建的完整流网络:
在这里插入图片描述
网络流说明与上方说明相同,此处不赘述。

(二)流网络中最大流与论文评审问题解的关系

首先,我们知道,流网络最大流下各边的流量就是一组值班问题的解:

  1. 当流网络流入汇点总量不为论文数与每篇论文需要评审数的积(m×a)时,说明有部分论文没有被规定数量(a)的评审评阅,此次论文评审问题无解;

  2. 当流网络流入汇点总量为论文数与每篇论文需要评审数的积(m×a)时,最大流为论文数与每篇论文需要评审数的积(m×a),此次论文评审问题有解。
    此时关键路径【评审→论文】中某条边的流量不为 0,说明这条边被选中,即出发点评审对终点论文进行了评阅。

第一层与第二层之间的最大容量保证了每位评审的最大论文评阅数,第二层与第三层间的边表示了评审与论文的关系,即是否评阅。第三层与汇点间的最大容量限制表示了每个论文需要评审的数量。

显然,如果这个问题有解,即每篇论文都有a位评审进行评阅,那么从论文层到汇点间边的流量必为最大容量限制a。此时,最后一层与第一层间所有路径容量必全部流满,则此时流网络必为最大流,即论文评审问题的解一定对应流网络中的最大流情况。且论文评审问题是否有解的依据是最大流是否大于论文数与每篇论文需要评审数的积(m×a)。

(三)最大流的计算

经过上述流网络的分析与构建,论文评审问题已经转化为求给定流网络的最大流问题。对于最大流的求解有很多种方式,本次实验将介绍Edmonds-Karp 算法改进后的 Dinic 算法。
接下来,将介绍 Edmonds-Karp 算法以及该算法涉及的关键定理,并介绍 Dinic 算法以及具体的Dinic 算法的实现方法。

1、Edmonds-Karp 算法

(1)算法思想:

因为所有流量都将从源点 s 出发,经过中间点后最终汇至汇点 t。因此最大流的网络可以拆分成一系列增广路的集合。其中,每条增广路的流量就是当前增广路上所有边的容量限制的最小值。因此可以通过不断搜索增广路径,并消去增广过程中产生的这条增广路径所消耗的流量,并不断更新流量完成最大流问题的求解。
在这里插入图片描述
由于增广路的搜索需要一定的顺序,不同的顺序会导致不同的结果。因此可能会因为搜索顺序不合适导致最大流求解错误。因此,可以引入残留网络,完成对错误搜索增广路产生的流量退回。
在残留网络中对每一条边增加一条反向边,其容量与原边相同,流量为原边最大限制容量与原边已使用流量之差。
在这里插入图片描述
如上图,不引入残留网络时可能先找到两条通路 ( A , A 1 , T ) (A,A1,T) (A,A1,T) ( A , A 2 , T ) (A,A2,T) (A,A2,T),这将导致流经后面 B1 时已经流量满,而无法连接节点造成最大流求解错误。引入残留网络后就可以将 ( A , A 1 , T ) (A,A1,T) (A,A1,T)这条通路给 B,最终将得到正确的最大流结果。

(2)算法关键定理及其证明:

①增广路定理:
残留网络中任何一条从 s 到 t 的有向通路都对应原图中一条增广路。只需求解出该道路中所有残量的最小值 d m i n d_{min} dmin,并把所有对应边流量增加 d m i n d_{min} dmin即可,这个过程被称为增广。显然,网络流中的流量可以增大,当且仅当当前网络中存在增广路。因此当残留网络中不存在增广路,则当前流即为最大流。这就是著名的增广路定理,它介绍了增广路解决最大流的思路,Edmonds-Karp算法和 Dinic 算法都是基于增广路方法的具体实现。

②证明增广路径长度递增:
不妨设 p p p为第一次 BFS找到的增广路,则 p p p 必为残留网络 ( s , t ) (s,t) (s,t)中最短路径。在进行增广后, p p p 上关键边 ( u , v ) (u,v) (u,v)将在残留网络中删去并增加反向边 ( v , u ) (v,u) (v,u)。设第一次找到的增广路径是 p = ( s → u → v → t ) p=(s→u→v→t) p=(suvt),关键边为 ( u , v ) (u,v) (u,v)。此时进行增广操作后,将从残留网络中删去正向边 ( u , v ) (u,v) (u,v),并增加反向边 ( v , u ) (v,u) (v,u)
为了证明增广路径长度递增,我们不妨假设下一次 BFS 搜索出现了长度更短的路径 p ′ p' p,则一定出现反向边 ( v , u ) , p ′ = ( s → v → u → t ) (v,u),p'=(s→v→u→t) (v,u)p=(svut)。而 BFS 性质保证第一次搜索中 d i s ( s , u ) dis(s,u) dis(s,u) d i s ( v , t ) dis(v,t) dis(v,t)都是最短的,此时有
d i s ( s , t ) = d i s ( s , u ) + d i s ( v , t ) + 1 dis(s,t)=dis(s,u)+dis(v,t)+1 dis(s,t)=dis(s,u)+dis(v,t)+1
若出现了更短的边,则有
∣ p ′ ∣ = d i s ′ ( s , v ) + d i s ′ ( u , t ) + 1 < ∣ p ∣ |p'|=dis'(s,v)+dis'(u,t)+1<|p| p=dis(s,v)+dis(u,t)+1<p

d i s ( s , v ) ≤ d i s ′ ( s , v ) , d i s ( u , t ) ≤ d i s ′ ( u , t ) dis(s,v)≤dis'(s,v),dis(u,t)≤dis'(u,t) dis(s,v)dis(s,v),dis(u,t)dis(u,t)
与假设矛盾,因此不存在长度更短的路径 p ′ p' p,即BFS 找到的增广路径长度是递增的。
在这里插入图片描述
③证明Edmonds-Karp算法迭代具有有穷上界
对于任一残留网络,在沿任一条增广路径增加流后,处于该条路径上所有关键边都将从残留网络中消失。并且任意一条增广路上都至少存在一条关键边。
因此,只需证明对于|E|中的每条边来说,其成为关键边的次数是有穷的并且为定值。此处先给出结论如下:
∣ E ∣ |E| E中的每条边成为关键边的次数最多为 ∣ V ∣ 2 \frac{|V|}{2} 2V

接下来给出证明:
不妨设 u 和 v 为集合 V 中的两个节点,且这两个节点由 E 中的一条有向边连通。由于增广路径都是最短路径,因此当边 ( u , v ) (u,v) (u,v)第一次成为关键边时,此时有:
δ f ( s , v ) = δ f ( s , u ) + 1 δ_f (s,v)=δ_f (s,u)+1 δf(s,v)=δf(s,u)+1
在对流进行增加后,边 ( u , v ) (u,v) (u,v)将被从残留网络中删除。并且,以后也不会重新出现,在另一条增广路径上,直到从 u u u v v v 的网络流减小后为止,并且只有当 ( u , v ) (u,v) (u,v)出现在增广路径上时,这种情况才会发生。如果当这一事件发生时 f ′ f' f G G G 的流,则有
δ f ′ ( s , u ) = δ f ′ ( s , v ) + 1 δ_f' (s,u)=δ_f' (s,v)+1 δf(s,u)=δf(s,v)+1
依②中证明,有:
δ f ( s , v ) ≤ δ f ′ ( s , v ) δ_f (s,v)≤δ_f' (s,v) δf(s,v)δf(s,v)
联立得:
δ f ′ ( s , u ) = δ f ′ ( s , v ) + 1 ≥ δ f ( s , v ) + 1 = δ f ( s , u ) + 2 δ_f' (s,u)=δ_f' (s,v)+1≥δ_f (s,v)+1=δ_f (s,u)+2 δf(s,u)=δf(s,v)+1δf(s,v)+1=δf(s,u)+2

因此,从边 ( u , v ) (u,v) (u,v)成为关键边到下一次再成为关键边,从源点 s s s 到节点 u u u 的距离至少增加两个单位,而从源点 s s s 到节点 u u u 的最初距离至少为0,从 s s s u u u 的最短路径上的中间节点不可能包括节点 s s s u u u 或者 t t t(因为边 ( u , v ) (u,v) (u,v)处于一条增广路径上意味着 u u u t t t 不同)。因此,一直到节点 u u u 成为不可达的节点前,其距离最多为 ∣ V ∣ − 2 |V|-2 V2。因此,在边 ( u , v ) (u,v) (u,v)第一次成为关键边时,它还可以至多再成为 ∣ V ∣ − 2 2 = ∣ V ∣ 2 − 1 \frac{|V|-2}{2}=\frac{|V|}{2}-1 2V2=2V1 次关键边,即边 ( u , v ) (u,v) (u,v)成为关键边的总次数为 ∣ V ∣ 2 \frac{|V|}{2} 2V。由于一共有O(E)对节点可以在一个残留网络中有边彼此连接,因此Edmonds-Karp算法执行的全部过程中,关键边的总数为 O ( V E ) O(VE) O(VE)。每条路径至少有一条关键边,原命题得证。

在使用 BFS 寻找增广路径时,每次迭代在 O ( E ) O(E) O(E)时间实现,Edmonds-Karp算法的时间复杂度因此为 O ( V E 2 ) O(VE^2) O(VE2)

2、Dinic 算法

(1)算法思想

Dinic 算法的思想也是分阶段地在层次网络中进行增广。它与 EK 算法的不同之处在于:Edmonds-Karp 算法每个阶段执行完一次 BFS 增广后,需要重新 BFS 从源点开始寻找另一条增广路;而 Dinic 中,只需一次 DFS 过程就可以实现多次增广。

不同于普通的 DFS,Dinic 算法的 DFS 并不是存在可行边就递归,还需要一层一层的进行,所以除了残留网络,Dinic 算法还需要层网络,即给节点定义一个层次,每个顶点的层次为当前顶点到达源点的最短距离。实际上该步操作与 BFS 寻找的最短路径相似,保证了每次 DFS 找到的增广路径的长度是相同的,同时保证了每次更新残留网络后,下一次找到的增广路径的长度必定是递增的,确保了算法的有穷性。
在这里插入图片描述

在基于生成的数据建立流网络时,就已经建立好了层次,因此本次实验中流网络一定能够给图分层,不会出现类似下图的的不能分层的网络。
在这里插入图片描述

(2)算法流程:

①用 BFS 建立分层图,注意分层图是以当前残留网络为基础建立的,所以要重复建立分层图;
②用 DFS 的方法寻找一条由源点到汇点的路径,获得这条路径的流量 V a V_a Va(路径上残量最小的边的残量)根据这条路径修改整个图,将所经之处正向边流量减少 V a V_a Va,反向边流量增加 V a V_a Va,注意 V a V_a Va是非负数;
③重复步骤 2,直到 DFS 找不到新的路径;重复步骤 1,直到图无法分层。

(3)算法实现与伪代码:

①bfs对顶点进行标号
在这里插入图片描述
②dfs在层次图中寻找增广
在这里插入图片描述
③调用Dinic算法求解最大流
在这里插入图片描述

(4)时间复杂度分析:

不妨设残留网络中顶点数为 V V V,边数为 E E E
①BFS 建立层网络,耗时 O ( E ) O(E) O(E)(与 EK 算法中 BFS 时间消耗一致);
②一次 DFS 中搜索出来的增广路径也存在关键边,且关键边的个数为 O ( E ) O(E) O(E),即一次 DFS 可能搜索出 O ( E ) O(E) O(E)条增广路径,对残留网络进行修改需要 O ( V ) O(V) O(V),所以一次 DFS 时间消耗为 O ( V E ) O(VE) O(VE)
③与 EK 算法相似,Dinic 算法存在层网络限制每次 DFS 找到的增广路径长度递增,且最大长度为 O ( V ) O(V) O(V)。综上,Dinic 算法的时间复杂度为
O ( V ) × ( O ( E ) + O ( V 2 E ) ) = O ( V 2 E ) O(V)×(O(E)+O(V^2 E))=O(V^2 E) O(V)×(O(E)+O(V2E))=O(V2E)

(四)求解具体分配方案:

对于本题,存在 n , m , a , b n,m,a,b n,m,a,b 共4个变量,为讨论 a , b a,b a,b间关系,不妨让 m = 10 , n = 3 m=10,n=3 m=10,n=3,即在有10篇论文和3个评审的情况下,讨论在不同的论文所需评审数 ( a ) (a) (a)和不同评审最大评阅论文数 ( b ) (b) (b)下的论文分配方案

a b 最大流 时间消耗 是否有解
1 20 10 0.0047ms 有解
2 15 20 0.0047ms 有解
3 10 30 0.004ms 有解
4 5 15 0.0034ms 无解
5 1 3 0.0032ms 无解

可以看到,对于一些不同a,b值下的有无解情况如上。此外,我又生成了大量数据,对不同n,m,a,b的值,发现存在如下规律
论文分配有解当且仅当 n × b ≥ m × a n×b≥m×a n×bm×a
通过分析,可以给出证明如下,对于此网络流,从源点发出的流量为 V s = b n V_s=bn Vs=bn,而有解的条件为最大流大于 V t = a m V_t=am Vt=am,又因为流网络不损失流,因此当有解时则有 V s ≥ V t V_s≥V_t VsVt,即 n × b ≥ m × a n×b≥m×a n×bm×a

四、实验结论或体会

  1. 日常生活中一些排班问题,分配问题,以及有先后关系的选课问题都可以通过网络流的方式进行解决
  2. 网络流问题解决过程中会遇到很多专有名词,了解这些名词是解决网络流问题的先决条件
  3. 可以使用有多种不同思路的算法求解最大流问题。这些算法的效率也不仅相同,应该分不同情况进行解决
  4. 最大流求解中的定理证明环环相扣,需要具备比较高的数学知识才能完成证明

五、思考

上面提及的两种算法均为增广路算法,即按照增广路径不断压入少量的流量,直到满流,而预流推进算法则是一次性将巨额流量压入网络,如果能够流就让他流,即将流量转到下一个节点,否则就溢出,不管溢出的部分。

1、算法主要思想

预流推进算法通过对单个结点的更新操作,直到没有结点需要更新来求解最大流。
算法过程维护的流函数不一定保持流守恒性,对于一个结点,我们允许进入结点的流超过流出结点的流,超过的部分被称为结点 u ( u ∈ V − { s , t } ) u(u∈V-\{s,t\}) u(uV{ s,t})的超额流 e ( u ) e(u) e(u)
e ( u ) = ∑ ( x , u ) ∈ E f ( x , u ) − ∑ ( u , y ) ∈ E f ( u , y ) e(u)=\sum_{(x,u)∈E}f(x,u)-\sum_{(u,y)∈E}f(u,y) e(u)=(x,u)Ef(x,u)(u,y)Ef(u,y)

e ( u ) > 0 e(u)>0 e(u)>0,称节点 u u u溢出。

预流推进算法维护每个结点的高度 h ( u ) h(u) h(u),并且规定溢出的结点 u u u如果要推送超额流,只能向高度小于 u u u的结点推送;如果 u u u没有相邻的高度小于 u u u的结点,就修改 u u u的高度(重贴标签)。

2、算法实现:

预流推进算法的实现基于以下几个部分:

①高度函数
准确地说,预流推进维护以下的一个映射 h : V → N h:V→N h:VN:
h ( s ) = ∣ V ∣ , h ( t ) = 0 h(s)=|V|,h(t)=0 h(s)=V,h(t)=0
∀ ( u , v ) ∈ E f , h ( u ) ≤ h ( v ) + 1 ∀(u,v)∈E_f,h(u)≤h(v)+1 (u,v)Ef,h(u)h(v)+1
h h h是残存网络 G f = ( V f , E f ) G_f=(V_f,E_f) Gf=(Vf,Ef)的高度函数。
引入定理:设 G f G_f Gf上的高度函数为 h h h,对于任意两个结点 u , v ∈ V u,v∈V u,vV,如果 h ( u ) > h ( v ) + 1 h(u)>h(v)+1 h(u)>h(v)+1,则 ( u , v ) (u,v) (u,v)不是 G f G_f Gf中的边。
算法只会在 h ( u ) = h ( v ) + 1 h(u)=h(v)+1 h(u)=h(v)+1的边执行推送。

②推送
适用条件:结点u溢出,且存在结点v,满足:
( u , v ) ∈ E f , c ( u , v ) − f ( u , v ) > 0 , h ( u ) = h ( v ) + 1 (u,v)∈E_f,c(u,v)-f(u,v)>0,h(u)=h(v)+1 (u,v)Ef,c(u,v)f(u,v)>0,h(u)=h(v)+1
则 push 操作适用于 ( u , v ) (u,v) (u,v)
于是,我们尽可能将超额流从 u u u推送到 v v v,推送过程中我们只关心超额流和 c ( u , v ) − f ( u , v ) c(u,v)-f(u,v) c(u,v)f(u,v)的最小值,不关心 v v v是否溢出。

如果 ( u , v ) (u,v) (u,v)在推送完之后满流,将其从残存网络中删除。

③重贴标签
适用条件:如果结点 u u u溢出,且 ∀ ( u , v ) ∈ E f , h ( u ) ≤ h ( v ) ∀(u,v)∈E_f,h(u)≤h(v) (u,v)Ef,h(u)h(v) ,则重贴标签操作适用于 u u u。则将 h ( u ) h(u) h(u)更新为 m i n ( u , v ) ∈ E f h ( v ) + 1 min_{(u,v)∈E_f } h(v)+1 min(u,v)Efh(v)+1即可。

④初始化
∀ ( u , v ) ∈ E , f ( u , v ) = { c ( u , v ) u=s 0 u ≠ s ∀(u,v)∈E,f(u,v)= \begin{cases} c(u,v)& \text{u=s}\\ 0& \text{u$\neq$s} \end{cases} (u,v)E,f(u,v)={ c(u,v)0u=su=s

∀ ( u ) ∈ V , h ( u ) = { ∣ V ∣ u=s 0 u ≠ s ∀(u)∈V,h(u)= \begin{cases} |V|& \text{u=s}\\ 0& \text{u$\neq$s} \end{cases} (u)V,h(u)={ V0u=su=s
e ( u ) = ∑ ( x , u ) ∈ E f ( x , u ) − ∑ ( u , y ) ∈ E f ( u , y ) e(u)=\sum_{(x,u)∈E}f(x,u)-\sum_{(u,y)∈E}f(u,y) e(u)=(x,u)Ef(x,u)(u,y)Ef(u,y)
上述将 ( s , v ) ∈ E (s,v)∈E (s,v)E充满流,并将 h ( s ) h(s) h(s)抬高,使得 ( s , v ) ∉ E (s,v)∉E (s,v)/E,因为 h ( s ) > h ( v ) h(s)>h(v) h(s)>h(v),而且 ( s , v ) (s,v) (s,v)毕竟满流,不必留在残存网络中;上述还将 e ( s ) e(s) e(s)初始化为 ∑ ( s , v ) ∈ E f ( s , v ) ∑_{(s,v)∈E}f(s,v) (s,v)Ef(s,v)的相反数。

具体进行操作过程中,按照顺序,只要存在结点 u u u满足推送或重贴标签操作的条件,就执行对应的操作,直至找不到节点 u u u,此时预流推送结束,最终流即为最大流。

3、引入优先队列进行优化

最高标号预流推进算法(High Level Preflow Push)是基于预流推进算法的优先队列实现,该算法优先推送高度高的溢出的结点,算法算法复杂度 O ( n 2 m ) O(n^2\sqrt{m}) O(n2m )
HLPP 算法具体过程如下:
①初始化(基于预流推进算法);
②选择溢出结点(除 s , t s,t s,t)中高度最高的结点 u u u,并对它所有可以推送的边进行推送;
③如果u仍溢出,对它重贴标签,回到步骤②;
④如果没有溢出的结点,算法结束。

4、BFS优化:

HLPP的上界为 O ( n 2 m ) O(n^2\sqrt{m}) O(n2m ),但在使用时卡得比较紧;我们可以在初始化高度的时候进行优化。具体来说,我们初始化 h ( u ) h(u) h(u) u u u t t t的最短距离;特别地 h ( s ) = n h(s)=n h(s)=n

此外,在 BFS 的同时我们顺便检查图的连通性,排除无解的情况。

5、GAP优化

HLPP推送的条件是 h ( u ) = h ( v ) + 1 h(u)=h(v)+1 h(u)=h(v)+1 ,而如果在算法的某一时刻, h ( u ) = t h(u)=t h(u)=t的结点个数为0,那么对于 h ( u ) > t h(u)>t h(u)>t的结点就永远无法推送超额流到 t t t,因此只能送回 s s s,那么我们就在这时直接让他们的高度变成 n + 1 n+1 n+1,以尽快推送回s,减少重贴标签的操作。

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/m0_46326495/article/details/118078244

智能推荐

从零开始搭建Hadoop_创建一个hadoop项目-程序员宅基地

文章浏览阅读331次。第一部分:准备工作1 安装虚拟机2 安装centos73 安装JDK以上三步是准备工作,至此已经完成一台已安装JDK的主机第二部分:准备3台虚拟机以下所有工作最好都在root权限下操作1 克隆上面已经有一台虚拟机了,现在对master进行克隆,克隆出另外2台子机;1.1 进行克隆21.2 下一步1.3 下一步1.4 下一步1.5 根据子机需要,命名和安装路径1.6 ..._创建一个hadoop项目

心脏滴血漏洞HeartBleed CVE-2014-0160深入代码层面的分析_heartbleed代码分析-程序员宅基地

文章浏览阅读1.7k次。心脏滴血漏洞HeartBleed CVE-2014-0160 是由heartbeat功能引入的,本文从深入码层面的分析该漏洞产生的原因_heartbleed代码分析

java读取ofd文档内容_ofd电子文档内容分析工具(分析文档、签章和证书)-程序员宅基地

文章浏览阅读1.4k次。前言ofd是国家文档标准,其对标的文档格式是pdf。ofd文档是容器格式文件,ofd其实就是压缩包。将ofd文件后缀改为.zip,解压后可看到文件包含的内容。ofd文件分析工具下载:点我下载。ofd文件解压后,可以看到如下内容: 对于xml文件,可以用文本工具查看。但是对于印章文件(Seal.esl)、签名文件(SignedValue.dat)就无法查看其内容了。本人开发一款ofd内容查看器,..._signedvalue.dat

基于FPGA的数据采集系统(一)_基于fpga的信息采集-程序员宅基地

文章浏览阅读1.8w次,点赞29次,收藏313次。整体系统设计本设计主要是对ADC和DAC的使用,主要实现功能流程为:首先通过串口向FPGA发送控制信号,控制DAC芯片tlv5618进行DA装换,转换的数据存在ROM中,转换开始时读取ROM中数据进行读取转换。其次用按键控制adc128s052进行模数转换100次,模数转换数据存储到FIFO中,再从FIFO中读取数据通过串口输出显示在pc上。其整体系统框图如下:图1:FPGA数据采集系统框图从图中可以看出,该系统主要包括9个模块:串口接收模块、按键消抖模块、按键控制模块、ROM模块、D.._基于fpga的信息采集

微服务 spring cloud zuul com.netflix.zuul.exception.ZuulException GENERAL-程序员宅基地

文章浏览阅读2.5w次。1.背景错误信息:-- [http-nio-9904-exec-5] o.s.c.n.z.filters.post.SendErrorFilter : Error during filteringcom.netflix.zuul.exception.ZuulException: Forwarding error at org.springframework.cloud..._com.netflix.zuul.exception.zuulexception

邻接矩阵-建立图-程序员宅基地

文章浏览阅读358次。1.介绍图的相关概念  图是由顶点的有穷非空集和一个描述顶点之间关系-边(或者弧)的集合组成。通常,图中的数据元素被称为顶点,顶点间的关系用边表示,图通常用字母G表示,图的顶点通常用字母V表示,所以图可以定义为:  G=(V,E)其中,V(G)是图中顶点的有穷非空集合,E(G)是V(G)中顶点的边的有穷集合1.1 无向图:图中任意两个顶点构成的边是没有方向的1.2 有向图:图中..._给定一个邻接矩阵未必能够造出一个图

随便推点

MDT2012部署系列之11 WDS安装与配置-程序员宅基地

文章浏览阅读321次。(十二)、WDS服务器安装通过前面的测试我们会发现,每次安装的时候需要加域光盘映像,这是一个比较麻烦的事情,试想一个上万个的公司,你天天带着一个光盘与光驱去给别人装系统,这将是一个多么痛苦的事情啊,有什么方法可以解决这个问题了?答案是肯定的,下面我们就来简单说一下。WDS服务器,它是Windows自带的一个免费的基于系统本身角色的一个功能,它主要提供一种简单、安全的通过网络快速、远程将Window..._doc server2012上通过wds+mdt无人值守部署win11系统.doc

python--xlrd/xlwt/xlutils_xlutils模块可以读xlsx吗-程序员宅基地

文章浏览阅读219次。python–xlrd/xlwt/xlutilsxlrd只能读取,不能改,支持 xlsx和xls 格式xlwt只能改,不能读xlwt只能保存为.xls格式xlutils能将xlrd.Book转为xlwt.Workbook,从而得以在现有xls的基础上修改数据,并创建一个新的xls,实现修改xlrd打开文件import xlrdexcel=xlrd.open_workbook('E:/test.xlsx') 返回值为xlrd.book.Book对象,不能修改获取sheett_xlutils模块可以读xlsx吗

关于新版本selenium定位元素报错:‘WebDriver‘ object has no attribute ‘find_element_by_id‘等问题_unresolved attribute reference 'find_element_by_id-程序员宅基地

文章浏览阅读8.2w次,点赞267次,收藏656次。运行Selenium出现'WebDriver' object has no attribute 'find_element_by_id'或AttributeError: 'WebDriver' object has no attribute 'find_element_by_xpath'等定位元素代码错误,是因为selenium更新到了新的版本,以前的一些语法经过改动。..............._unresolved attribute reference 'find_element_by_id' for class 'webdriver

DOM对象转换成jQuery对象转换与子页面获取父页面DOM对象-程序员宅基地

文章浏览阅读198次。一:模态窗口//父页面JSwindow.showModalDialog(ifrmehref, window, 'dialogWidth:550px;dialogHeight:150px;help:no;resizable:no;status:no');//子页面获取父页面DOM对象//window.showModalDialog的DOM对象var v=parentWin..._jquery获取父window下的dom对象

什么是算法?-程序员宅基地

文章浏览阅读1.7w次,点赞15次,收藏129次。算法(algorithm)是解决一系列问题的清晰指令,也就是,能对一定规范的输入,在有限的时间内获得所要求的输出。 简单来说,算法就是解决一个问题的具体方法和步骤。算法是程序的灵 魂。二、算法的特征1.可行性 算法中执行的任何计算步骤都可以分解为基本可执行的操作步,即每个计算步都可以在有限时间里完成(也称之为有效性) 算法的每一步都要有确切的意义,不能有二义性。例如“增加x的值”,并没有说增加多少,计算机就无法执行明确的运算。 _算法

【网络安全】网络安全的标准和规范_网络安全标准规范-程序员宅基地

文章浏览阅读1.5k次,点赞18次,收藏26次。网络安全的标准和规范是网络安全领域的重要组成部分。它们为网络安全提供了技术依据,规定了网络安全的技术要求和操作方式,帮助我们构建安全的网络环境。下面,我们将详细介绍一些主要的网络安全标准和规范,以及它们在实际操作中的应用。_网络安全标准规范