首页 > 编程语言 >有限制的 bellman_ford 算法

有限制的 bellman_ford 算法

时间:2024-03-10 20:35:11浏览次数:34  
标签:dist int bellman ford ++ 算法 edge backup id

题目链接

1.有限制的 \(Bellman\_Ford\)

时间复杂度: \(O(N*M)\)

在传统的 \(Bellman\_Ford\) 中,可以处理边数不大于 \(K\) 条边的最短距离
但我们只要加一条限制(实际上只多了两行代码)
就可以实现求恰好等于 \(K\) 条边的最短距离
具体的就在于其核心代码中:

 for(int i = 0; i < k; i ++ )    //最大经过几条边就迭代几次
    {           
        memcpy(backup, dist, sizeof dist);
        for(int j = 0; j < m; j ++ )    //遍历所有边更新最短路
        {
            int a = edge[j].a, b = edge[j].b, w = edge[j].w;
            dist[b] = min(dist[b], backup[a] + w);  //每次更新到顶点b的边
        }
    }

其中为什么要拷贝一份 \(dist\) 数组就不解释了
我们只要将上述代码改为:

    for (int i = 0; i < k; i++) {
        memcpy(backup, d, sizeof(d));
        //与最多经过k条边这里不同!
        memset(d, 0x3f, sizeof(d)); //add
        for (int j = 0; j < m; j++) {
            int a = edges[j].a, b = edges[j].b, c = edges[j].c;
            //与最多经过k条边这里不同!
            d[b] = min(d[b], backup[a] + c);
            d[a] = min(d[a], backup[b] + c);//add,可以与上面的交换位置
        }
    }

最大的不同在于我们拷贝完 \(dist\) 数组之后,反手将 \(dist\) 数组初始化为正无穷了
这样在下一次松弛操作的时候,我们就必须进行松弛了,因为任何数肯定小于这个正无穷
只不过在松弛的时候,不仅要松弛 \(dsit[b]\),还要松弛 \(dist[a]\)

#pragma GCC optimize(2) //累了就吸点氧吧~

#include <iostream>
#include <cstring>
#include <algorithm>
#include <unordered_map>

using namespace std;

const int N = 210, M = 1000010;

int n, m, st, en, k;
int dist[N], backup[N];
unordered_map<int, int> id;
struct Edge{//Bellman_Ford的数据结构为三元组
    int a, b, c;
}edge[M];

int Bellman_Ford()
{
    memset(dist, 0x3f, sizeof dist);
    dist[id[st]] = 0;
    
    for(int i = 0; i < k; i ++ )
    {
        memcpy(backup, dist, sizeof dist);//是在外层循环copy的!!!
        memset(dist, 0x3f, sizeof dist);
        for(int j = 0; j < m; j ++ )
        {
            int a = edge[j].a, b = edge[j].b, c = edge[j].c;
            dist[b] = min(dist[b], backup[a] + c);
            dist[a] = min(dist[a], backup[b] + c);
        }
    }
    return dist[id[en]];
}

int main()
{
    cin >> k >> m >> st >> en;
    if(!id.count(st))   id[st] = ++ n;
    if(!id.count(en))   id[en] = ++ n;
    
    for(int i = 0; i < m; i ++ )
    {
        int a, b, c;
        cin >> c >> a >> b;//这道题比较恶心,需要先读入边长
        if(!id.count(a)) id[a] = ++ n;
        if(!id.count(b)) id[b] = ++ n;
        edge[i] = {id[a], id[b], c};
    }
    
    // cout << n << endl;
    // for(int i = 1; i <= n; i ++ )   cout << dist[i] << " \n"[i == n];
    
    cout << Bellman_Ford() << endl; 
    return 0;
}

2.倍增思想Floyd

参考:
1
2
3

标签:dist,int,bellman,ford,++,算法,edge,backup,id
From: https://www.cnblogs.com/ALaterStart/p/18064735

相关文章

  • 算法题 - Shuffling Machine
    Introduction:Shufflingisaprocedureusedtorandomizeadeckofplayingcards.Becausestandardshufflingtechniquesareseenasweak,andinordertoavoid"insidejobs"whereemployeescollaboratewithgamblersbyperforminginadequatesh......
  • 算法学习
    今天复习巩固了深搜和广度搜索,做了几个练习题,其中求细胞数量注意审题,即让我们求连通块的个数。#include<bits/stdc++.h>usingnamespacestd;intx,y;charm[105][105];intsx[4]={-1,0,1,0};//左上右下intsy[4]={0,-1,0,1};voidbfs(inta,intb){ m[a][b]='0'; for(......
  • RIPEMD算法:多功能哈希算法的瑰宝
    一、RIPEMD算法的起源与历程RIPEMD(RACEIntegrityPrimitivesEvaluationMessageDigest)算法是由欧洲研究项目RACE发起,由HansDobbertin、AntoonBosselaers和VincentRijmen共同设计的一种哈希算法。RIPEMD算法最早发布于1996年,旨在提供一种安全、高效的数据完整性验证工具。......
  • 贪心算法
    例题1、硕鼠的交易题目描述ProblemDescription小老鼠准备了M磅的猫粮,准备去和看守仓库的猫做交易,因为仓库里有小老鼠喜欢吃的五香豆。仓库有N个房间;第i个房间有J[i]磅的五香豆,并且需要用F[i]磅的猫粮去交换;老鼠不必交换该房间所有的五香豆,换句话说,它可以用F[i]a%磅的......
  • 基于肤色模型和中值滤波的手部检测算法FPGA实现,包括tb测试文件和MATLAB辅助验证
    1.算法运行效果图预览RTL图:   仿真图:   导入到matlab显示效果如下:   2.算法运行软件版本matlab2022a vivado2019.2 3.算法理论概述      在计算机视觉领域,基于肤色模型和中值滤波的手部检测方法是一种常见的初步定位策略。该方法主要分为......
  • ST算法
    记录9:212024-3-10ST算法其实就是利用倍增的思想去划分区间利用ST算法求RMQ问题(区间最值问题)\(F[i,j]表示数列A在子区间[i,i+2^j-1]里数的最大值F[i,0]=A[i]\)\(F[i,j]=max(F[i,j-1],F[i+2^{j-1},j-1])\)求[l,r]最值的时候求出满足\(2^k<r-l......
  • KMP算法(基于代码随想录)的随笔
    KMPKMP的主要思想是当出现字符串不匹配时,可以知道一部分之前已经匹配的文本内容,可以利用这些信息避免从头再去做匹配了。前缀表:起始位置到下标i之前(包括i)的子串中,有多大长度的相同前缀后缀。那么使用KMP可以解决两类经典问题:匹配问题:28.实现strStr()(opensnewwindow)重......
  • SHA算法:数据完整性的守护者
    一、SHA算法的起源与演进SHA(SecureHashAlgorithm)算法是一种哈希算法,最初由美国国家安全局(NSA)设计并由国家标准技术研究所(NIST)发布。SHA算法的目的是生成数据的哈希值,用于验证数据的完整性和真实性。最早的SHA-0版本于1993年发布,之后陆续发布了SHA-1、SHA-2和SHA-3等不同版本,不......
  • Hanoi问题及其相关快速算法
    Hanoi问题抽象hanoi(n,x,y,z)step1:hanoi(n-1,x,z,y)step2:move(x,z)step3:hanoi(n-1,y,x,z)递归部分实现代码voidhanoi(intn,charx,chary,charz){​ if(n==1){ // 递归出口​ move(x,z);​ }​ else{​ hanoi(n-1,x,z,y);​ move(x,z);​ hanoi(n......
  • 基于Harris角点的室内三维全景图拼接算法matlab仿真
    1.算法运行效果图预览   2.算法运行软件版本matlab2022a 3.算法理论概述      在室内三维全景图的构建中,Harris角点检测算法扮演着关键的角色,用于识别场景中的特征点以实现图像间的匹配和对齐。该过程通常包括以下几个步骤:图像获取、角点检测、特征描述、匹......