zoukankan      html  css  js  c++  java
  • 学习笔记·堆优化$mathscr{dijkstra}$

    嘤嘤嘤今天被迫学了这个算法……其实对于学习图论来说我内心是拒绝的(mathscr{qnq})

    由于发现关于这个(mathscr{SPFA})的时间复杂度(O(kE))中的(k approx 2)好像只针对于稀疏图?(emmm)想不到时间复杂度居然还有数据分治这一说(ORZ)

    好的,对于我的图论而言,好像只会(MST)(mathscr{MT Law})和最短路?哦呵呵呵呵那可真优秀啊(QAQ)

    要不是今天上午学了堆优化的,没准我连普通的都不会了!


    回归正题,最朴素的(mathscr{dijkstra})的思想是我们要从已知的点里面选一个离源点最近的,然后以此不断松弛周围的点(代码显性),并保存这个点的最短路(代码隐性)。而(dijkstra)遵循的是贪心思想,就是在边权都是正的的情况下,当前找到的最短路一定是对于这个点全局最优,因为不会再有更短的路径了——而显然这个贪心在有负权边的时候的错误的。

    于是我们发现,对于其中“找到最近的点”,即当前记录的(dist_i)最小的(i),是有优化性可言的。朴素是(O(n))的查询,加上堆之后就可以变成(O(logn))。所以原本时间复杂度(O(mn))(dijkstra)就可以优化成(O(mlogn)),并且相对稳定。

    于是核心的代码就是这一部分啦~

    inline void dijistra(){
        fill(dist + 1, dist + N + 1, 2147483647) ; 
        q.push((node){S, 0}) ; dist[S] = 0 ;
        while(!q.empty()){
            node qwq = q.top() ; q.pop() ;
            x1 = qwq.t, x2 = qwq.v ;
            if(vis[x1]) continue ; vis[x1] = 1 ;
            for(k = head[x1]; k ; k = e[k].next){
                dist[e[k].to] = min(dist[e[k].to], x2 + e[k].v) ;
                q.push((node){e[k].to, dist[e[k].to]}) ;
            }
        }
    

    (qwq)就这样了

  • 相关阅读:
    包和常用内置模块(二)
    常用内置模块(一)
    正则表达式和re模块
    迭代器和生成器
    函数(四)
    函数(三)闭包函数与装饰器
    Codeforces Round #539 (Div. 2) D 思维
    Codeforces Round #539 (Div. 2) 异或 + dp
    Codeforces Round #546 (Div. 2) E 推公式 + 线段树
    牛客练习赛42 C 反着计算贡献
  • 原文地址:https://www.cnblogs.com/pks-t/p/9368525.html
Copyright © 2011-2022 走看看