算法设计与分析多段图问题

动态规划-多段图问题

时间复杂度分析:

这份代码用到了两种方法:

  • 1 遍历每个相邻阶段,下一个阶段只会依赖于前一个阶段,通过不断遍历,逐渐把最终结果转移到起始节点。时间复杂度平均下来为 O(n2/k)
  • 2 时间复杂度为O(n * k)
运行结果

在这里插入图片描述

代码:
#include <iostream>
#include <cstring>
#include <vector>

using namespace std;

int g[9][9], cost[9];
vector<int> layer[6];

void initLayer(){
	layer[0].push_back(0), layer[1].push_back(1),layer[1].push_back(2);
	layer[2].push_back(3), layer[2].push_back(4),layer[2].push_back(5);
	layer[3].push_back(6), layer[3].push_back(7),layer[4].push_back(8);
}

void initGraph(){
	memset(g, 0x3f, sizeof g);
	g[0][1] = 5, g[0][2] = 2, g[1][3] = 3, g[1][4] = 3, g[2][3] = 6;
	g[2][4] = 5, g[2][5] = 8, g[3][6] = 1, g[3][7] = 4, g[4][6] = 6;
	g[4][7] = 2, g[5][6] = 6, g[5][7] = 2, g[6][8] = 7, g[7][8] = 3;
}

int main()
{
	initLayer();
	initGraph();
	//1.第一种做法: -----------------------------------------------------
	memset(cost, 0x3f, sizeof cost);
	cost[8] = 0;
	for(int i = 3; i >= 0; i --)
	{
		int j = i + 1;
		int cnta = i, cntb = j;
		for(int x = 0; x < layer[cnta].size(); x ++)
		{
			for(int y = 0; y < layer[cntb].size(); y ++)
			{
				int a = layer[cnta][x], b = layer[cntb][y];
				if(g[a][b] == 0x3f3f3f3f) continue;
				cost[a] = min(cost[a], cost[b] + g[a][b]);
			}
		}
	}
	cout << "最短路径长度为:" << cost[0] << endl;
	
	
	
	//第二种做法; -------------------------------------------------------------
	memset(cost, 0x3f, sizeof cost);
	cost[8] = 0;
	for(int i = 8; i >= 0; i --)
	{
		for(int j = i + 1; j <= 8; j ++)
		{
			if(g[i][j] == 0x3f3f3f3f) continue;
			cost[i] = min(cost[i], cost[j] + g[i][j]);	
		}	
	} 
	vector<int> res;
	res.push_back(0);
	int nextv = 0;
	for(int i = 0; i <= 3; i ++)   //每次都选取 i 节点所达节点最小的 cost[j] 
	{
		int minv = 0x3f3f3f3f;
		int cntv = 0;
		for(int j = 0; j <= 8; j ++)
		{
			if(g[nextv][j] == 0x3f3f3f3f) continue;
			if(cost[j] + g[nextv][j] < minv){
				cntv  = j;
				minv = cost[j] + g[nextv][j];
			}
		}
		nextv = cntv;
		res.push_back(cntv);
	}
	cout << "最短路径长度为:" << cost[0] << endl;
	for(int x = 0; x < res.size(); x ++)
	{
		if(x != res.size() - 1)
			cout << res[x] << "-->";
		else cout << res[x] << endl;
	}
	
	return 0;
} 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

王奇hh

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值