上下界网络流

【总结】有上下界网络流 说在前面 说明 无源汇上下界可行流 有源汇上下界可行流 有源汇上下界最大流 有源汇上下界最小流 说在前面 鶸鶸cosi以前做上下界网络流的题只会打板,并没有了解到算法本质。好久没有打过板的cosi今天考试果然在一道上下界最大流上挂了TAT。于是决定好好学习一下上下界网络流,下面是一些粗浅的理解,没有附代码,相信大家在众多博客中都找得到(雾)。 上下界网络流主要强调对初始流和附加... 阅读详情

I. DEFINITION

上下界网络问题

  1. 每条边不仅有一个容量上限C,还有容量下限b;
  2. 像普通网络流一样,也要满足除源点汇点外的每一个点, i n x = o u t x in_x=out_x inx​=outx​

II. 无源点汇点上下界可行流([LOJ]#115. 无源汇有上下界可行流)

因为没有源点和汇点,那么每一个点都需要保证流量守恒;
可行流的意思是可以分配出来,但不要求最大;

Solution:

  1. 对于每一个节点 x x x,流入的下界之和 i n x in_x inx​,流出的下界之和 o u t x out_x outx​,如果 i n x > o u t x in_x>out_x inx​>outx​,那么可理解为多流入的流量来自虚拟源点 s s s,反之流入 T T T
  2. 为了是每一个节点X的流入流出流量守恒,那么应该将较少的那一端的流量往上多分配一些,使得 i n x = o u t x in_x=out_x inx​=outx​,同时往上分配的容量不应该突破该条边的上限 C C C
  3. 跑一遍从 S S S到 T T T的最大流,如果最大流的流量等于 S S S连接所有边的流量之和

TIME COMPLEXITY

与 d i n i c dinic dinic时间复杂度相等
O ( d i n i c ( n 2 ∗ m ) ) O(dinic(n^2*m)) O(dinic(n2∗m))

Code:

#include<bits/stdc++.h>
using namespace std;
const int maxn=100005;
const int INF=0x3f3f3f3f;
int n,m,S,T,cnt=0,maxflow,ans,tot=1,sum;
int head[maxn],dep[maxn],vis[maxn],in[maxn],out[maxn],b[maxn],c[maxn];
inline int read()
{
	int s=0,f=1;
	char c=getchar();
	while (c<'0'||c>'9')
	{
		if (c=='-')
		{
			f=-1;
		}
		c=getchar();
	}
	while (c>='0'&&c<='9')
	{
		s=s*10+c-48;
		c=getchar();
	}
	return s*f;
}
struct node
{
	int from,to,next;
	int val;
}edge[maxn];
inline void add(int x,int y,int z)
{
	edge[++tot].next=head[x];
	edge[tot].from=x;
	edge[tot].to=y;
	edge[tot].val=z;
	head[x]=tot;
	edge[++tot].next=head[y];
	edge[tot].from=y;
	edge[tot].to=x;
	edge[tot].val=0;
	head[y]=tot;
}
inline bool bfs()
{
	queue<int>q;
	memset(dep,-1,sizeof(dep));
	dep[S]=1;
	q.push(S);
	while(!q.empty())
	{
		int u=q.front();
		q.pop();
		for(int i=head[u];i;i=edge[i].next)
		{
			int to=edge[i].to,w=edge[i].val;
			if(dep[to]==-1&&w>0)
			{
				dep[to]=dep[u]+1;
				q.push(to);
			}
		}
	}
	if (dep[T]==-1)
	{
		return 0;
	}
	return 1;
}
inline int dfs(int u,int low)
{
	if (u==T)
	{
		return low;
	}
	int ret=low;
	for (int i=head[u];i;i=edge[i].next)
	{
		int to=edge[i].to,w=edge[i].val;
		if (dep[to]==dep[u]+1&&w>0)
		{
			int flow=dfs(to,min(ret,w));
			if (flow>0)
			{
				edge[i].val-=flow;
				edge[i^1].val+=flow;
			}
			ret-=flow;
			if (!ret)
			{
				break;
			}
		}
	}
	return low-ret;
}
inline void dinic()
{
    while (bfs())
    {
		maxflow+=dfs(S,INF);
	}
}
int main()
{
	n=read(),m=read();
	S=0,T=n+1;
	for (int i=1;i<=m;i++)
	{
		int x=read(),y=read();
		b[i]=read(),c[i]=read();
		add(x,y,c[i]-b[i]);
		in[y]+=b[i];
		out[x]+=b[i];
	}
	for (int i=1;i<=n;i++)
	{
		int dif=in[i]-out[i];
		if (dif>0)
		{
			add(S,i,dif);
			sum+=dif;
		}
		else
		{
			add(i,T,out[i]-in[i]);
		}
	}
//	dinic();
	while (bfs())                   //从S到T跑最大流
    {
		maxflow+=dfs(S,INF);
	}
	if (maxflow!=sum)
	{
		cout<<"NO"<<endl;
		return 0;
	}
	else
	{
		cout<<"YES"<<endl;
		for (int i=1;i<=m;i++)
		{
			//注意最后加的浮动流量应该是反边的流量 edge[(i<<1)|1],正向边是剩余的流量
			//反边要不要异或1取决于tot从几开始
			cout<<edge[(i<<1)|1].val+b[i]<<endl;
		}
	}
	return 0;
}

III. 有源点汇点上下界可行流

S S S和 T T T不需要守恒。将 T T T向 S S S建一条下界为零,上界为 I N F INF INF的边
流量为 t t t到 S S S的反边的流量

与上一题几乎一模一样

IV. 有源点汇点上下界最大流([LOJ]#116. 有源汇有上下界最大流)

Solution:

在可行流的前提下满足最大流

  1. 按照无源点汇点上下界可行流建图
  2. 额外添加 t t t到 s s s的边,容量下界为 0 0 0,上界为 I N F INF INF
  3. 跑一遍 S S S到 T T T的最大流,得到一个可行流 f l o w 1 flow1 flow1
  4. 删掉 t t t到 s s s的边跑一遍 s s s到 t t t的最大流,得到 f l o w 2 flow2 flow2
  5. a n s = f l o w 1 + f l o w 2 ans=flow1+flow2 ans=flow1+flow2

Code:

#include<bits/stdc++.h>
using namespace std;
const int maxn=100005;
const int INF=0x3f3f3f3f;
int n,m,s,t,S,T,cnt=0,maxflow,ans,tot=1,sum,flow,flow1,flow2;
int head[maxn],dep[maxn],vis[maxn],in[maxn],out[maxn],b[maxn],c[maxn];
inline int read()
{
	int s=0,f=1;
	char c=getchar();
	while (c<'0'||c>'9')
	{
		if (c=='-')
		{
			f=-1;
		}
		c=getchar();
	}
	while (c>='0'&&c<='9')
	{
		s=s*10+c-48;
		c=getchar();
	}
	return s*f;
}
struct node
{
	int from,to,next;
	int val;
}edge[maxn];
inline void add(int x,int y,int z)
{
	edge[++tot].next=head[x];
	edge[tot].from=x;
	edge[tot].to=y;
	edge[tot].val=z;
	head[x]=tot;
	edge[++tot].next=head[y];
	edge[tot].from=y;
	edge[tot].to=x;
	edge[tot].val=0;
	head[y]=tot;
}
inline bool bfs()
{
	queue<int>q;
	memset(dep,-1,sizeof(dep));
	dep[S]=1;
	q.push(S);
	while(!q.empty())
	{
		int u=q.front();
		q.pop();
		for(int i=head[u];i;i=edge[i].next)
		{
			int to=edge[i].to,w=edge[i].val;
			if(dep[to]==-1&&w>0)
			{
				dep[to]=dep[u]+1;
				q.push(to);
			}
		}
	}
	if (dep[T]==-1)
	{
		return 0;
	}
	return 1;
}
inline int dfs(int u,int low)
{
	if (u==T)
	{
		return low;
	}
	int ret=low;
	for (int i=head[u];i;i=edge[i].next)
	{
		int to=edge[i].to,w=edge[i].val;
		if (dep[to]==dep[u]+1&&w>0)
		{
			int flow=dfs(to,min(ret,w));
			if (flow>0)
			{
				edge[i].val-=flow;
				edge[i^1].val+=flow;
			}
			ret-=flow;
			if (!ret)
			{
				break;
			}
		}
	}
	return low-ret;
}
inline void dinic()
{
    while (bfs())
    {
		maxflow+=dfs(S,INF);
	}
}
int main()
{
	n=read(),m=read(),s=read(),t=read();
	tot=1;
	for(int i = 1; i <= m; i++)
	{
		int x=read(),y=read();
		b[i]=read(),c[i]=read();
		in[y]+=b[i];
		out[x]+=b[i];
		add(x,y,c[i]-b[i]);
	}
	S=0,T=n+1;                                  //虚拟源点和汇点
	for (int i=1;i<=n;i++)
	{
		if (in[i]-out[i]>0)
		{
			add(S,i,in[i]-out[i]);
			sum=sum+(in[i]-out[i]);
		}
		else
		{
			add(i,T,out[i]-in[i]);
		}
	}
	add(t,s,INF); 								//添加1条 t到s的边,容量inf。反边也需要,容量为0
	//寻找可行流
	while (bfs()==true)                         //从S到T跑最大流
	{
		flow=dfs(S,INF);
		maxflow+=flow;
	}
	if (maxflow!=sum)
	{
		cout<<"please go home to sleep"<<"\n";
		return 0;
	}
	flow1=edge[tot].val;                        //记录“可行流”的大小,注意应该取t到s的反边的流量
	edge[tot].val=edge[tot-1].val=0;            //删掉 t到s的边,等效于将流量设为0
	//跑一边s到t的最大流
	S=s,T=t;
	flow=0;
	flow2=0;
	while (bfs()==true)                         //跑最大流
	{
		flow=dfs(S,INF);
		flow2+=flow;
	}
	cout<<flow1+flow2<<endl;                    //可行流+最大流 得到最终的最大流
	return 0;
}

V. 有源点汇点上下界最小流

Solution:

  1. 按照有源点汇点上下界可行流建图,求出 f l o w 1 flow1 flow1
  2. 删掉 t t t到 s s s的边,跑一边原图 t t t到 s s s的最大流,得到 f l o w 2 flow2 flow2
  3. a n s = f l o w 1 − f l o w 2 ans=flow1-flow2 ans=flow1−flow2

Notice:这题链式前向星用结构体会TLE一个点!!!

Code:

#include<bits/stdc++.h>
using namespace std;
const int maxn=500005;
const int INF=0x3f3f3f3f;
int n,m,s,t,S,T,cnt,maxflow,ans,tot=1,sum,flow,flow1,flow2;
int head[maxn],to[maxn],edge[maxn],nxt[maxn],dep[maxn],vis[maxn],in[maxn],out[maxn],b[maxn],c[maxn];
inline int read()
{
	int s=0,f=1;
	char c=getchar();
	while (c<'0'||c>'9')
	{
		if (c=='-')
		{
			f=-1;
		}
		c=getchar();
	}
	while (c>='0'&&c<='9')
	{
		s=s*10+c-48;
		c=getchar();
	}
	return s*f;
}
inline void add(int x,int y,int z)
{
	to[++tot]=y;
	edge[tot]=z;
	nxt[tot]=head[x];
	head[x]=tot;
	to[++tot]=x;
	edge[tot]=0;
	nxt[tot]=head[y];
	head[y]=tot;
}
inline bool bfs()
{
	queue<int>q;
	memset(dep,-1,sizeof(dep));
	dep[S]=1;
	q.push(S);
	while(!q.empty())
	{
		int u=q.front();
		q.pop();
		for(int i=head[u];i;i=nxt[i])
		{
			int To=to[i],w=edge[i];
			if (dep[To]==-1&&w>0)
			{
				dep[To]=dep[u]+1;
				q.push(To);
			}
		}
	}
	if (dep[T]==-1)
	{
		return 0;
	}
	return 1;
}
inline int dfs(int u,int low)
{
	if (u==T)
	{
		return low;
	}
	int ret=low;
	for (int i=head[u];i;i=nxt[i])
	{
		int To=to[i],w=edge[i];
		if (dep[To]==dep[u]+1&&w>0)
		{
			int flow=dfs(To,min(ret,w));
			if (flow==0)
			{
				dep[To]=0;
			}
			if (flow>0)
			{
				edge[i]-=flow;
				edge[i^1]+=flow;
			}
			ret-=flow;
			if (!ret)
			{
				break;
			}
		}
	}
	return low-ret;
}
inline void dinic()
{
    while (bfs())
    {
		maxflow+=dfs(S,INF);
	}
}
signed main()
{
	n=read(),m=read(),s=read(),t=read();
	tot=1;
	for(int i=1;i<=m;i++)
	{
		int x=read(),y=read();
		b[i]=read(),c[i]=read();
		in[y]+=b[i];
		out[x]+=b[i];
		add(x,y,c[i]-b[i]);
	}
	S=0,T=n+1;                                  //虚拟源点和汇点
	for (int i=1;i<=n;i++)
	{
		if (in[i]-out[i]>0)
		{
			add(S,i,in[i]-out[i]);
			sum=sum+(in[i]-out[i]);
		}
		else
		{
			add(i,T,out[i]-in[i]);
		}
	}
	add(t,s,INF); 								//添加1条 t到s的边,容量inf。反边也需要,容量为0
	//寻找可行流
	while (bfs()==true)                         //从S到T跑最大流
	{
		flow=dfs(S,INF);
		maxflow+=flow;
	}
	if (maxflow!=sum)
	{
		cout<<"please go home to sleep"<<"\n";
		return 0;
	}
	flow1=edge[tot];                        //记录“可行流”的大小,注意应该取t到s的反边的流量
	edge[tot]=edge[tot-1]=0;            //删掉 t到s的边,等效于将流量设为0
	//跑一边s到t的最大流
	S=t,T=s;
	flow=0;
	flow2=0;
	while (bfs()==true)                         //跑最大流
	{
		flow=dfs(S,INF);
		flow2+=flow;
	}
	cout<<flow1-flow2<<endl;                    //可行流+最大流 得到最终的最大流
	return 0;
}
//链式前向星用struct会T!!!
/*
#include<bits/stdc++.h>
using namespace std;
#define int long long
const int maxn=500005;
const int INF=0x3f3f3f3f;
int n,m,s,t,S,T,cnt=0,maxflow,ans,tot=1,sum,flow,flow1,flow2;
int head[maxn],dep[maxn],vis[maxn],in[maxn],out[maxn],b[maxn],c[maxn];
inline int read()
{
	int s=0,f=1;
	char c=getchar();
	while (c<'0'||c>'9')
	{
		if (c=='-')
		{
			f=-1;
		}
		c=getchar();
	}
	while (c>='0'&&c<='9')
	{
		s=s*10+c-48;
		c=getchar();
	}
	return s*f;
}
struct node
{
	int from,to,next;
	int val;
}edge[maxn];
inline void add(int x,int y,int z)
{
	edge[++tot].next=head[x];
	edge[tot].from=x;
	edge[tot].to=y;
	edge[tot].val=z;
	head[x]=tot;
	edge[++tot].next=head[y];
	edge[tot].from=y;
	edge[tot].to=x;
	edge[tot].val=0;
	head[y]=tot;
}
inline bool bfs()
{
	queue<int>q;
	memset(dep,-1,sizeof(dep));
	dep[S]=1;
	q.push(S);
	while(!q.empty())
	{
		int u=q.front();
		q.pop();
		for(int i=head[u];i;i=edge[i].next)
		{
			int to=edge[i].to,w=edge[i].val;
			if(dep[to]==-1&&w>0)
			{
				dep[to]=dep[u]+1;
				q.push(to);
			}
		}
	}
	if (dep[T]==-1)
	{
		return 0;
	}
	return 1;
}
inline int dfs(int u,int low)
{
	if (u==T)
	{
		return low;
	}
	int ret=low;
	for (int i=head[u];i;i=edge[i].next)
	{
		int to=edge[i].to,w=edge[i].val;
		if (dep[to]==dep[u]+1&&w>0)
		{
			int flow=dfs(to,min(ret,w));
			if (flow>0)
			{
				edge[i].val-=flow;
				edge[i^1].val+=flow;
			}
			ret-=flow;
			if (!ret)
			{
				break;
			}
		}
	}
	return low-ret;
}
inline void dinic()
{
    while (bfs())
    {
		maxflow+=dfs(S,INF);
	}
}
signed main()
{
	n=read(),m=read(),s=read(),t=read();
	tot=1;
	for(int i = 1; i <= m; i++)
	{
		int x=read(),y=read();
		b[i]=read(),c[i]=read();
		in[y]+=b[i];
		out[x]+=b[i];
		add(x,y,c[i]-b[i]);
	}
	S=0,T=n+1;                                  //虚拟源点和汇点
	for (int i=1;i<=n;i++)
	{
		if (in[i]-out[i]>0)
		{
			add(S,i,in[i]-out[i]);
			sum=sum+(in[i]-out[i]);
		}
		else
		{
			add(i,T,out[i]-in[i]);
		}
	}
	add(t,s,INF); 								//添加1条 t到s的边,容量inf。反边也需要,容量为0
	//寻找可行流
	while (bfs()==true)                         //从S到T跑最大流
	{
		flow=dfs(S,INF);
		maxflow+=flow;
	}
	if (maxflow!=sum)
	{
		cout<<"please go home to sleep"<<"\n";
		return 0;
	}
	flow1=edge[tot].val;                        //记录“可行流”的大小,注意应该取t到s的反边的流量
	edge[tot].val=edge[tot-1].val=0;            //删掉 t到s的边,等效于将流量设为0
	//跑一边s到t的最大流
	S=t,T=s;
	flow=0;
	flow2=0;
	while (bfs()==true)                         //跑最大流
	{
		flow=dfs(S,INF);
		flow2+=flow;
	}
	cout<<flow1-flow2<<endl;                    //可行流+最大流 得到最终的最大流
	return 0;
}
*/

VI. 无源点汇点上下界最小费用可行流

Solution:

  1. 按照无源点汇点上下界可行流建图,把原图中 x − > y x->y x−>y 的边,建一条容量 u p p e r − l o w e r upper-lower upper−lower,费用为 c o s t cost cost的边,其他边的费用设为 0 0 0即可
  2. 跑最小费用最大流即可
  3. 最终最小的费用 = = == ==所有边的下界流量*对应的费用的和 + + +最小费用最大流的费用

VII. 有源点汇点上下界最小费用可行流

Solution:

在VI的基础上,额外增加一条t到s的边,容量是INF,费用为0;

VIII. [LGOJ]P4043 [AHOI2014/JSOI2014]支线剧情

Solution:

  1. 对于一条边 x − > y x->y x−>y,容量下界设为 1 1 1,上界设为 I N F INF INF,表示每个剧情最多被覆盖一次,上不封顶;费用就是时间
  2. 原图中源点 s : 1 s:1 s:1,汇点 t : 0 t:0 t:0, 1 1 1到 n n n的每个点 i i i都向 t t t连一条下界为 0 0 0,上界 I N F INF INF,费用为 0 0 0的边,意思是没个点都可以终结剧情
  3. 然后统计每个点的 i n x in_x inx​, o u t x out_x outx​按照无源点汇点建图,要么是 S S S连 x x x,要么是 x x x连 T T T,费用都设为 0 0 0,容量就是 i n x in_x inx​和 o u t x out_x outx​之差;
  4. 额外的一条边 t t t到 s s s,容量 I N F INF INF,费用 0 0 0;
  5. 跑一边从 S S S到 T T T的最小费用最大流 c o s t 2 cost2 cost2,再统计每条边的下界流量*对应费用的和 c o s t 1 cost1 cost1; c o s t 1 + c o s t 2 cost1+cost2 cost1+cost2

Code:

#include<bits/stdc++.h>
using namespace std;
const int maxn=100005;
const int inf=0x3f3f3f3f;
int n,s=1,t,S,T,tot=1,maxflow,cost1,cost2;
int head[maxn],pre[maxn],level[maxn],in[maxn],out[maxn],dis[maxn],increase[maxn];
bool vis[maxn];
struct node
{
	int from,to,next,flow,cost;
}edge[maxn];
inline int read()
{
	int s=0,f=1;
	char c=getchar();
	while (c<'0'||c>'9')
	{
		if (c=='-')
		{
			f=-1;
		}
		c=getchar();
	}
	while (c>='0'&&c<='9')
	{
		s=s*10+c-48;
		c=getchar();
	}
	return s*f;
}
inline void add(int x,int y,int z,int f)
{
	edge[++tot].next=head[x];
	edge[tot].to=y;
	edge[tot].flow=z;
	edge[tot].cost=f;
	head[x]=tot;
	
	edge[++tot].next=head[y];
	edge[tot].to=x;
	edge[tot].flow=0;
	edge[tot].cost=-f;
	head[y]=tot;
}
inline bool spfa()
{
	memset(vis,0,sizeof(vis));
	memset(dis,0x7f,sizeof(dis));
	memset(increase,0x7f,sizeof(increase));
	queue<int> q;
	q.push(S);
	vis[S]=true;
	dis[S]=0;
	while (q.empty()==false)
	{
		int x=q.front();
		q.pop();
		vis[x]=false;
		for (int i=head[x];i;i=edge[i].next)
		{
			int y=edge[i].to;
			if (edge[i].flow>0&&dis[x]+edge[i].cost<dis[y])
			{
				dis[y]=dis[x]+edge[i].cost;
				increase[y]=min(increase[x],edge[i].flow);
				pre[y]=i;
				if (vis[y]==false)
				{
					q.push(y);
					vis[y]=true;
				}
			}
		}
	}
	return dis[T]<0x7f7f7f7f;
}

inline void update()
{
	int cur=T;
	while (cur!=S)
	{
		int last=pre[cur];
		edge[last].flow-=increase[T];
		edge[last^1].flow+=increase[T];
		cur=edge[last^1].to;
	}
	maxflow+=increase[T];
	cost2+=dis[T]*increase[T];
	return ;
}

int main()
{
	n=read();
	for (int i=1;i<=n;i++)
	{
		int k=read();
		if (i!=1)
		{
			add(i,t,inf,0);
		}
		for (int j=1;j<=k;j++)
		{
			int nxt=read(),tim=read();
			in[nxt]+=1;
			out[i]+=1;
			cost1=cost1+1*tim;
			add(i,nxt,inf-1,tim);
		}
	}
	S=n+1,T=n+2;
	for (int i=0;i<=n;i++)
	{
		if (in[i]-out[i]>0)
		{
			add(S,i,in[i]-out[i],0);
		}
		else
		{
			add(i,T,out[i]-in[i],0);
		}
	}
	add(t,s,inf,0);
	while (spfa()==true)
	{
		update();
	}
	cout<<cost1+cost2<<endl;
	return 0;
}
/*
6
2 2 1 3 2
2 4 3 5 4
2 5 5 6 6
0
0
0
*/
周源-有上下界的网络流周源-有上下界的网络流 周源-有上下界的网络流周源-有上下界的网络流周源-有上下界的网络流周源-有上下界的网络流 立即下载

相关推荐

Hive中的四种排序方式(order by,sort by,distribute by,cluster by)使用与区别详解

在平时的Hive数仓开发工作中经常会用到排序,而Hive中支持的排序方式有四种,这里结合具体的案例详细介绍一下他们的使用与区别: order by sort by distribute by cluster by 一、order by(全局排序) 1、作用:全局排序,只有一个reducer。 order by 会对输入做全局排序,因此只有一个reducer(多个reducer无法保证全局有序),也正因为只有一个reducer,所以当输入的数据规模较大时会导致计算时间较长。   set hive.mapr

weixin_43230682的博客 1万+

[学习笔记] 上下界网络流

上下界网络流。

Oxide‘s Blog 702

智能座舱(七)——智能音频系统

本文剖析车载智能音频系统的核心技术,聚焦音响、功放、麦克风和广播收音机四大组件。音响系统通过多声道布局(如23扬声器阵列)结合动态声场校准算法,实现三维声场覆盖;功放系统采用高效D类技术,支持OTA音效调整和故障自愈;麦克风阵列运用波束成形技术实现精准拾音,并保障隐私安全;广播系统融合数字与网络技术提升音质。核心在于硬件标准化与算法差异化的协同,未来将朝集成化、AI个性化方向发展。

DC20160101的博客 1573

【学习笔记】上下界网络流

昨天刚刚被神秘建图方式打败了。今天又发现连知识点都没学完……

七代目鸽影 490

知识图谱与人工智能本体论:构建机器认知的语义基石

本文探讨了知识图谱与人工智能本体论如何作为机器认知的语义基石,让AI从‘知道数据’迈向‘理解知识’。文章详细拆解了本体论的核心构件与构建方法,并阐述了从本体到知识图谱的实践路径,包括知识获取、融合、存储及推理应用,最终分析了其在智能搜索与专家系统等场景中带来的根本性重塑。

nginx7reverse的博客 910

字节跳动已上岸测试工程师的面试经验

这个时候发面经已经有点晚了,所以现在打算让这篇面经主要面向即将秋招的童鞋,当然现在还在春招的童鞋也可以看哈,我和大家一起聊聊关于测试的二三事。   一、测试工程师的工作是什么?   测试工程师简单点说就是找bug,然后反馈给开发人员,不要小看这个工作。   首先很明显的bug开发人员有时候自己就能找到,测试人员要有比开发人员更加全面的想法才能找到深层次的问题点,   其次,要端正一个态度就是测试人员不是一个电脑小白,相反国外顶级的测试开发工程师同时也是顶级的开发工程师甚至更厉害,所以作为一个测试工程师一定要

m0_60745607的博客 2933

浅谈上下界网络流

背景最近一直在做这类题目…… 感觉题目变化还是挺多的 就在这里总结一下好了……首先Orz Lynstery 本文参考博客:有上下界的网络流学习笔记——by liu_runda正文上下界网络流,显然就是对每条边有上下界流量限制的网络流问题 众人:这不废话嘛 对于上下界网络流问题,最重要的思想是“转化” 因为学习后你会发现:处理每一种情形都是要由前一种更为简单的情形转化过来,然后用同样的方法

linkfqy 5108

Fluent基于低氧舱气体交换仿真(氮气与空气混合)

一、背景概述 模拟低氧舱充氮气和排除混合气体的过程,假设注入95%的氮气,舱内原有气体为空气,压力为标准大气压,温度为300K。观察气体注入过程中,舱内平均氮气和氧气浓度的变化。 二、Fluent设置 Setup 1、General type选择压力基 绝对速度 瞬态 重力勾选 2、Model 能量方程开启 组分运输开启,设置方法如下: 选择后OK,view就会变成Edit,点击Edit。然后再次点击Edit。 将组分中的非氮气氧气和空气的气体移除,右边选项需要将空气放在最后一位。 3、Materi

qq_35535616的博客 1万+

有上下界的网络流问题

有上下界的网络流问题详细讲解:有源汇可行流+无源汇可行流/最小流/最大流。

Regina8023 4592

保姆级避坑指南:在openEuler 22.03 LTS上用kubeadm 1.32.2部署K8s集群(含阿里云镜像加速)

本文提供在openEuler 22.03 LTS上使用kubeadm 1.32.2部署Kubernetes集群的详细指南,涵盖系统准备、容器运行时适配、kubeadm配置及集群初始化等关键步骤。特别针对openEuler系统的特殊性,解决软件源配置、cri-dockerd编译安装、阿里云镜像加速等常见问题,帮助用户高效完成K8s集群部署。

weixin_28312391的博客 273

新手必读!2025最全AI智能体入门手册,50个问题全讲透

感知(Perception):能读取环境,比如读取网页数据、识别用户输入、接入 API;思考(Reasoning/Planning):理解任务目标,规划出行动步骤;行动(Action):调工具、查资料、发消息、写入数据库……直接执行任务。有了这三步,智能体才不是“一个会说话的大模型”,而是真正的“能落地执行的工作代理人”。多个 Agent 分工协作,每个智能体负责一个角色或任务节点,像一个“虚拟团队”。一个爬数据的 Agent,一个提炼要点的 Agent,一个撰写报告的 Agent,

互联网架构师笔记 1968

【图论】上下界网络流算法

上下界网络流详解:涵盖无源汇/有源汇可行流、最大/最小流算法原理,提供完整C++实现,深入解析转化思想与应用。

zhangmohan123321的博客 1239

什么是垂直同步?电脑快速消除屏幕撕裂与提升游戏性能的方法 垂直同步、游戏画面撕裂、游戏优化、VSync、FPS、FreeSync、G-Sync、显卡驱动更新、游戏画质、输入延迟

看这张动图,左边的画面出现了明显“切开”的断层现象,而右边画面非常流畅,没有撕裂。这正是「垂直同步」开关的区别。:每秒生成多少帧图像。比如 60FPS 表示一秒钟显示 60 张图片。刷新率(Refresh Rate):显示器每秒刷新几次画面,单位是赫兹(Hz)。60Hz 表示每秒刷新 60 次。参数说明FPS显卡渲染速度(逻辑帧率)刷新率显示器的显示频率(物理限制)当 FPS 高于刷新率时,显卡渲染的画面来不及被显示器显示,导致撕裂。屏幕撕裂(Screen Tearing)

代码简单说 Vue、JAVA、PHP、Node.js 熟练运用,接口、架构、性能全搞定。 1347

【有上下界的网络流】

相对于一般的网络流,有上下界的网络流的某些边多出了流量下界的限制,如边u->v,上下界为high、low,如果有流经过这条边,这个流必须在[low,high]这个区间内。这类题目主要要求解决下面三个问题,“有源汇、无源汇的可行流”、“有源汇的最大流”、“有源汇的最小流”,注意这里所说的源汇是原网络中的源汇,分别记为s、t。   这类题目的难点在于下界的限制很难处理,我们将所有有下界限制的边中分离

leolin_的专栏 4208

深度学习工具包 DeepLearningToolbox

深度学习工具包Deprecation notice.-----This toolbox is outdated and no longer maintained.There are much better tools available for deep learning than this toolbox, e.g. [Theano](http://deeplearning.net/software/theano/), [torch](http://torch.ch/) or [tensorflow](http://www.tensorflow.org/)I would suggest you use one of the tools mentioned above rather than use this toolbox.Best, Rasmus.DeepLearnToolbox================A Matlab toolbox for Deep Learning.Deep Learning is a new subfield of machine learning that focuses on learning deep hierarchical models of data.It is inspired by the human brain's apparent deep (layered, hierarchical) architecture.A good overview of the theory of Deep Learning theory is[Learning Deep Architectures for AI](http://www.iro.umontreal.ca/~bengioy/papers/ftml_book.pdf)For a more informal introduction, see the following videos by Geoffrey Hinton and Andrew Ng.* [The Next Generation of Neural Networks](http://www.youtube.com/watch?v=AyzOUbkUf3M) (Hinton, 2007)* [Recent Developments in Deep Learning](http://www.youtube.com/watch?v=VdIURAu1-aU) (Hinton, 2010)* [Unsupervised Feature Learning and Deep Learning](http://www.youtube.com/watch?v=ZmNOAtZIgIk) (Ng, 2011)If you use this toolbox in your research please cite [Prediction as a candidate for learning deep hierarchical models of data](http://www2.imm.dtu.dk/pubdb/views/publication_details.php?id=6284)```@MASTERSTHESIS\{IMM2012-06284, author = "R. B. Palm", title = "Prediction as a candidate for learning deep hierarchical models of data", year = "2012",}```Contact: rasmusbergpalm at gmail dot comDirectories included in the toolbox-----------------------------------`NN/` - A library for Feedforward Backpropagation Neural Networks`CNN/` - A library for Convolutional Neural Networks`DBN/` - A library for Deep Belief Networks`SAE/` - A library for Stacked Auto-Encoders`CAE/` - A library for Convolutional Auto-Encoders`util/` - Utility functions used by the libraries`data/` - Data used by the examples`tests/` - unit tests to verify toolbox is workingFor references on each library check REFS.mdSetup-----1. Download.2. addpath(genpath('DeepLearnToolbox'));Example: Deep Belief Network---------------------```matlabfunction test_example_DBNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit RBM and visualize its weightsrand('state',0)dbn.sizes = [100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);figure; visualize(dbn.rbm{1}.W'); % Visualize the RBM weights%% ex2 train a 100-100 hidden unit DBN and use its weights to initialize a NNrand('state',0)%train dbndbn.sizes = [100 100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);%unfold dbn to nnnn = dbnunfoldtonn(dbn, 10);nn.activation_function = 'sigm';%train nnopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.10, 'Too big error');```Example: Stacked Auto-Encoders---------------------```matlabfunction test_example_SAEload mnist_uint8;train_x = double(train_x)/255;test_x = double(test_x)/255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit SDAE and use it to initialize a FFNN% Setup and train a stacked denoising autoencoder (SDAE)rand('state',0)sae = saesetup([784 100]);sae.ae{1}.activation_function = 'sigm';sae.ae{1}.learningRate = 1;sae.ae{1}.inputZeroMaskedFraction = 0.5;opts.numepochs = 1;opts.batchsize = 100;sae = saetrain(sae, train_x, opts);visualize(sae.ae{1}.W{1}(:,2:end)')% Use the SDAE to initialize a FFNNnn = nnsetup([784 100 10]);nn.activation_function = 'sigm';nn.learningRate = 1;nn.W{1} = sae.ae{1}.W{1};% Train the FFNNopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.16, 'Too big error');```Example: Convolutional Neural Nets---------------------```matlabfunction test_example_CNNload mnist_uint8;train_x = double(reshape(train_x',28,28,60000))/255;test_x = double(reshape(test_x',28,28,10000))/255;train_y = double(train_y');test_y = double(test_y');%% ex1 Train a 6c-2s-12c-2s Convolutional neural network %will run 1 epoch in about 200 second and get around 11% error. %With 100 epochs you'll get around 1.2% errorrand('state',0)cnn.layers = { struct('type', 'i') %input layer struct('type', 'c', 'outputmaps', 6, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %sub sampling layer struct('type', 'c', 'outputmaps', 12, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %subsampling layer};cnn = cnnsetup(cnn, train_x, train_y);opts.alpha = 1;opts.batchsize = 50;opts.numepochs = 1;cnn = cnntrain(cnn, train_x, train_y, opts);[er, bad] = cnntest(cnn, test_x, test_y);%plot mean squared errorfigure; plot(cnn.rL);assert(er<0.12, 'Too big error');```Example: Neural Networks---------------------```matlabfunction test_example_NNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);% normalize[train_x, mu, sigma] = zscore(train_x);test_x = normalize(test_x, mu, sigma);%% ex1 vanilla neural netrand('state',0)nn = nnsetup([784 100 10]);opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samples[nn, L] = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.08, 'Too big error');%% ex2 neural net with L2 weight decayrand('state',0)nn = nnsetup([784 100 10]);nn.weightPenaltyL2 = 1e-4; % L2 weight decayopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex3 neural net with dropoutrand('state',0)nn = nnsetup([784 100 10]);nn.dropoutFraction = 0.5; % Dropout fraction opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex4 neural net with sigmoid activation functionrand('state',0)nn = nnsetup([784 100 10]);nn.activation_function = 'sigm'; % Sigmoid activation functionnn.learningRate = 1; % Sigm require a lower learning rateopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex5 plotting functionalityrand('state',0)nn = nnsetup([784 20 10]);opts.numepochs = 5; % Number of full sweeps through datann.output = 'softmax'; % use softmax outputopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex6 neural net with sigmoid activation and plotting of validation and training error% split training data into training and validation datavx = train_x(1:10000,:);tx = train_x(10001:end,:);vy = train_y(1:10000,:);ty = train_y(10001:end,:);rand('state',0)nn = nnsetup([784 20 10]); nn.output = 'softmax'; % use softmax outputopts.numepochs = 5; % Number of full sweeps through dataopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, tx, ty, opts, vx, vy); % nntrain takes validation set as last two arguments (optionally)[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');```[![Bitdeli Badge](https://d2weczhvl823v0.cloudfront.net/rasmusbergpalm/deeplearntoolbox/trend.png)](https://bitdeli.com/free "Bitdeli Badge")

廖雪峰Python教程[完整版]

廖雪峰的python教程整理的,已经排好版了,而且还是完整的,适合小白

【ALGO】网络流(5) 上下界网络流

上下界网络流例题解析

0x00 729

SAP B1中文培訓教材_SDK

公司内部培训资料,对开发工具 ,DIAPI, UIAPI,Add-ON有详细解说

上下界网络流 (更新中)

最近刚学了上下界网络流,写篇博客梳理下知识。 大佬的博客: https://oi.men.ci/network-flow-with-bounds/ 何为上下界网络流? 其和普通的网络流的区别就在于每条边的流量不仅有上界,同时还有一个下界,普通网络流的下界是0。 无源无汇上下界可行流 问题: 给出一个上下界网络流图,问是否存在一条可行流。 做法:添加超级源点S,超级汇点T,这里对边进行拆解,对于一条...

Link_Ray的博客 417

win10 跳过U8环境检测的IE WebControls.rar

win10 安装u8的时候 提示IE WebControls 不通过,这个工具可以欺骗u8的检查。 跳过U8环境检测的IE WebControls。提示导入失败后,重新检测通过。

有上下界的网络流 学习笔记

预备知识f(u,v)f(u,v)表示u->v这条边的实际流量 b(u,v)b(u,v)表示u->v这条边的流量下界 c(u,v)c(u,v)表示u->v这条边的流量上界 在一个无源汇的普通网络流图中,满足 0≤f(u,v)≤c(u,v)0\le f(u,v)\le c(u,v) ∑f(u,i)=∑f(i,v)\sum f(u,i)=\sum f(i,v) 分别称为流量限制条件和流量平衡条件

zyf2000 7707

有上下界的网络流

转自http://blog.youkuaiyun.com/regina8023/article/details/45815023 写在前面 有上下界的网络流即对边的流量有限制,必须在[down,up]的范围内。 其实普通的网络流也是一种特殊的有上下界的网络流,只是每条边的流量限制为[0,cap]。 分类 有上下界的网络流分为两种: 有源汇  所有点都要求满足流量平

hao_zong_yin的博客 677

模板 - 上下界网络流

整理的算法模板合集: ACM模板 目录无源汇上下界可行流有源汇上下界最大流有源汇上下界最小流 无源汇上下界可行流 /* 首先建立一个源S和一个汇T,一般称为附加源和附加汇。 对于图中的每条弧<u,v>,假设它容量上界为c,下界b,那么把这条边拆为三条只有上界的弧。 一条为<S,v>,容量为b;   一条为<u,T>,容量为b;   一条为<u,v>,容量为c-b。 其中前两条弧一般称为附加弧。 然后对这张图跑最大流,

繁凡さん的博客 543
上一篇: [LGOJ]P3147 [USACO16OPEN]262144 P
下一篇: 迭代加深搜索(iddfs)
Modestr-E·X·L
博客等级 码龄7年 5粉丝 20原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值