国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式

這篇具有很好參考價值的文章主要介紹了第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點擊"舉報違法"按鈕提交疑問。

裸題:904. 蟲洞

904. 蟲洞 - AcWing題庫
第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式,AcWing算法提高課 課程記錄,圖論

// 蟲洞是負(fù)權(quán)且單向邊,道路是正權(quán)且雙向邊,題目較裸,判斷有無負(fù)環(huán)即可
#include <iostream>
#include <cstring>
using namespace std;

const int N = 510, M = 6010;
int h[N], e[M], ne[M], w[M], idx;
int n, m, k;
int dis[N], cnt[N];
int q[N];
bool st[N];

void add(int x, int y, int d)
{
    e[idx] = y, ne[idx] = h[x], w[idx] = d, h[x] = idx ++ ;
}

bool spfa()
{
    int tt = 0, hh = 0;
    memset(cnt, 0, sizeof(cnt));
    memset(dis, 0, sizeof(dis));
    memset(st, 0, sizeof(st));
    for (int i = 1; i <= n; ++ i ) st[i] = true, q[tt ++ ] = i;
    while (hh != tt)
    {
        int x = q[hh ++ ];
        if (hh == N) hh = 0;
        st[x] = false;
        for (int i = h[x]; i != -1; i = ne[i])
        {
            int y = e[i];
            if (dis[y] > dis[x] + w[i])
            {
                cnt[y] = cnt[x] + 1;
                if (cnt[y] >= n) return true;
                dis[y] = dis[x] + w[i];
                if (!st[y]) 
                {
                    st[y] = true;
                    q[tt ++ ] = y;
                    if (tt == N) tt = 0;
                }
            }
        }
    }
    return false;
}

int main()
{
    int T;
    scanf("%d", &T);
    while (T -- )
    {
        memset(h, -1, sizeof(h));
        idx = 0;
        scanf("%d%d%d", &n, &m, &k);
        int x, y, d;
        for (int i = 0; i < m; ++ i )
        {
            scanf("%d%d%d", &x, &y, &d);
            add(x, y, d), add(y, x, d);
        }
        for (int i = 0; i < k; ++ i )
        {
            scanf("%d%d%d", &x, &y, &d);
            add(x, y, -d);
        }
        if (spfa()) puts("YES");
        else puts("NO");
    }
    return 0;
}

第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式,AcWing算法提高課 課程記錄,圖論
這個==真的服,調(diào)半天,還有,鄰接表的大小又設(shè)置錯了


01分?jǐn)?shù)規(guī)劃:361. 觀光奶牛

361. 觀光奶牛 - AcWing題庫
第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式,AcWing算法提高課 課程記錄,圖論

在圖論問題中,所有形如:某個部分之和除以某個部分之和最大的問題,被稱為01分?jǐn)?shù)規(guī)劃,通常使用二分解決這類問題
根據(jù)題意,這道題的答案范圍在 ( 0 , 1000 ] (0, 1000] (0,1000]中,我們需要二分這個區(qū)間找到答案
若點權(quán)之和/邊權(quán)之和大于等于mid,則說明答案在 [ m i d , r ] [mid, r] [mid,r]之間
反之,點權(quán)之和/邊權(quán)小于mid,則說明答案在 [ l , m i d ] [l, mid] [l,mid]之間
根據(jù)這個二段性,我們能二分出ans,使得邊權(quán)之和/邊權(quán)之和的最大值 = ans

現(xiàn)在的問題是check如何實現(xiàn)?
整理不等式,如下圖:
第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式,AcWing算法提高課 課程記錄,圖論

一個常用的技巧:若圖中的環(huán)既有點權(quán)又有邊權(quán),那么可以將點權(quán)加到出邊或者入邊上
那么不等式的求和可以提到外面,結(jié)合這個技巧,將點權(quán)和邊權(quán)結(jié)合
若一條邊由x->y,權(quán)值為w,那么將其權(quán)值設(shè)置為 f x ? m i d ? w f_x-mid*w fx??mid?w, f x f_x fx?為x的點權(quán)
問題就轉(zhuǎn)換成了圖中是否存在一個正環(huán)?
求正環(huán)只要修改三角不等式即可:dis[y] < dis[x] + w[i]

總結(jié)下:check判斷圖中是否存在一個環(huán),其點權(quán)之和/邊權(quán)之和大于等于mid,轉(zhuǎn)換成圖中是否存在一個正環(huán)(或權(quán)值和為0的環(huán)),若存在,則l = mid,否則r = mid,

  1. 思考題目的二段性
  2. 根據(jù)不等式重置邊/點權(quán)
  3. 根據(jù)不等式判斷題目的具體問題:負(fù)環(huán)/最小生成樹/最短路
#include <iostream>
#include <cstring>
using namespace std;

const int N = 1010, M = 5010;
int h[N], e[M], ne[M], w[M], idx;
int f[N];
double dis[N];
int cnt[N]; bool st[N];
int q[N];

int n, m;

void add(int x, int y, int d)
{
    e[idx] = y, ne[idx] = h[x], w[idx] = d, h[x] = idx ++ ;
}

bool check(double mid)
{
    memset(dis, 0, sizeof(dis));
    memset(cnt, 0, sizeof(cnt));
    int tt = 0, hh = 0;
    
    for (int i = 1; i <= n; ++ i ) st[i] = true, q[tt ++ ] = i;
    while (hh != tt)
    {
        int x = q[hh ++ ];
        if (hh == N) hh = 0;
        st[x] = false;
        for (int i = h[x]; i != -1; i = ne[i])
        {
            int y = e[i];
            if (dis[y] <= dis[x] + f[x] - mid * w[i])
            {
                dis[y] = dis[x] + f[x] - mid * w[i];
                cnt[y] = cnt[x] + 1;
                if (cnt[y] >= n) return true;
                if(!st[y])
                {
                    st[y] = true;
                    q[tt ++ ] = y;
                    if (tt == N) tt = 0;
                }
            }
        }
    }
    return false;
}

int main()
{
    memset(h, -1, sizeof(h));
    scanf("%d%d", &n, &m);
    for (int i = 1; i <= n; ++ i ) scanf("%d", &f[i]);
    int x, y, d;
    for (int i = 0; i < m; ++ i )
    {
        scanf("%d%d%d", &x, &y, &d);
        add(x, y, d);
    }
    
    double l = 0, r = 1000;
    while (r - l > 1e-4)
    {
        double mid = (l + r) / 2;
        if (check(mid)) l = mid;
        else r = mid;
    }
    
    printf("%.2lf\n", r);
    return 0;
}

debug:點權(quán)需要從數(shù)組1號下標(biāo)開始讀取


特殊建圖與01分?jǐn)?shù)規(guī)劃+trick:1165. 單詞環(huán)

1165. 單詞環(huán) - AcWing題庫
第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式,AcWing算法提高課 課程記錄,圖論

估算一下這題的數(shù)據(jù)量,如果按照題意建圖,不僅爆空間還會爆時間,所以這題需要考慮其他建圖方式
第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式,AcWing算法提高課 課程記錄,圖論

題目給定的建圖方式是:單詞為點,若兩單詞能相連,那么邊的權(quán)值為1
考慮新的建圖方式,以單詞的前兩個字符為起點,最后兩個字符為終點,建立一條有向邊,權(quán)值為單詞的長度。這種建圖方式中,點的數(shù)量最多為26 * 26,邊的數(shù)量為 1 0 5 10^5 105

其次,題目要求環(huán)中所有單詞的長度之和 / 環(huán)中的單詞數(shù)量最大,顯然是01分?jǐn)?shù)規(guī)劃
二分答案,答案的范圍是 ( 0 , 1000 ] (0, 1000] (0,1000],最大的答案為每個單詞長度都是1000,而最小的答案0是取不到的,最小的情況應(yīng)該是1,0用來表示無解
整理不等式,重新設(shè)置邊權(quán)為 w i ? 1 ? m i d w_i - 1 * mid wi??1?mid,1是由環(huán)中點的數(shù)量累加后(第二個式子)再把累加提到外面(第三個等式)得到的
check:每次根據(jù)mid判斷圖中是否存在正環(huán)或零環(huán),若存在返回true,反之返回false

trick:如果spfa更新了很多次還沒有結(jié)束循環(huán),那么有極大概率可以認(rèn)為圖中存在環(huán),這里設(shè)置閾值為10000(點數(shù)的十幾倍),當(dāng)循環(huán)次數(shù)超過該值時,直接認(rèn)為圖中存在環(huán)、
不過這樣的trick在正規(guī)比賽中不會出現(xiàn)

#include <iostream>
#include <cstring>
using namespace std;

const int N = 27 * 27, M = 1e5 + 10;
int h[N], e[M], ne[M], w[M], idx;
double dis[N];
int cnt[N], q[N];
bool st[N];

void add(int x, int y, int d)
{
    e[idx] = y, ne[idx] = h[x], w[idx] = d, h[x] = idx ++ ;
}

bool check(double mid)
{
    memset(dis, 0, sizeof(dis));
    memset(cnt, 0, sizeof(cnt));
    int tt = 0, hh = 0, count = 0;
    for (int i = 0; i < N - 1; ++ i ) q[tt ++ ] = i, st[i] = true;
    while (hh != tt )
    {
        int x = q[hh ++ ];
        if (hh == N) hh = 0;
        st[x] = false;
        for (int i = h[x]; i != -1; i = ne[i])
        {
            int y = e[i];
            if (dis[y] <= dis[x] + w[i] - mid)
            {
                cnt[y] = cnt[x] + 1;
                if (cnt[y] >= N) return true;
                if (++ count >= 10000) return true;
                dis[y] = dis[x] + w[i] - mid;
                if (!st[y])
                {
                    st[y] = true;
                    q[tt ++ ] = y;
                    if (tt == N) tt = 0;
                }
            }
        }
    }
    return false;
}

int main()
{
    int m;
    char str[1010];
    while (scanf("%d", &m), m)
    {
        memset(h, -1, sizeof(h));
        idx = 0;
        for (int i = 0; i < m; ++ i )
        {
            scanf("%s", str);
            int len = strlen(str);
            if (len >= 2)
            {
                int x = (str[0] - 'a') * 26 + str[1] - 'a';
                int y = (str[len - 2] - 'a') * 26 + str[len - 1] - 'a';
                add(x, y, len);
            }
        }
        
        double l = 0, r = 1000;
        while (r - l > 1e-4)
        {
            double mid = (l + r) / 2;
            if (check(mid)) l = mid;
            else r = mid;
        }
        
        if (r < 1e-4) puts("No solution");
        else printf("%.2lf\n", r);
    }
    return 0;
}

debug:dis數(shù)組的類型開成int,想著邊的權(quán)值為整數(shù),int就行,然而邊權(quán)被重置,類型是浮點數(shù)文章來源地址http://www.zghlxwxcb.cn/news/detail-635136.html

到了這里,關(guān)于第三章 圖論 No.6負(fù)環(huán)之01分?jǐn)?shù)規(guī)劃與特殊建圖方式的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實不符,請點擊違法舉報進(jìn)行投訴反饋,一經(jīng)查實,立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • 第三章 圖論 No.4最小生成樹的簡單應(yīng)用

    第三章 圖論 No.4最小生成樹的簡單應(yīng)用

    存在邊權(quán)為負(fù)的情況下,無法求最小生成樹 裸題:1140. 最短網(wǎng)絡(luò) 1140. 最短網(wǎng)絡(luò) - AcWing題庫 套個prim的板子即可 裸題:1141. 局域網(wǎng) 1141. 局域網(wǎng) - AcWing題庫 裸題,稀疏圖,套個kruskal的板子就行 需要注意的是:題目給定的圖可能存在多個連通塊,若使用prim算法,需要對每個連通

    2024年02月14日
    瀏覽(31)
  • 第三章 圖論 No.11二分圖,匈牙利算法與點覆蓋

    第三章 圖論 No.11二分圖,匈牙利算法與點覆蓋

    257. 關(guān)押罪犯 - AcWing題庫 最大最小問題,一眼二分 答案的范圍在 [ 1 , 1 e 9 ] [1, 1e9] [ 1 , 1 e 9 ] 之間,二分答案,check(mid) check:將所有權(quán)值大于mid的邊進(jìn)行二分,若能得到二分圖,返回true,否則返回false 最終將得到最優(yōu)解ans,所有大于ans的邊組成的圖為二分圖,若是圖中有邊

    2024年02月12日
    瀏覽(19)
  • 第三章 圖論 No.8最近公共祖先lca, tarjan與次小生成樹

    第三章 圖論 No.8最近公共祖先lca, tarjan與次小生成樹

    O ( m l o g n ) O(mlogn) O ( m l o g n ) ,n為節(jié)點數(shù)量,m為詢問次數(shù),lca是一種在線處理詢問的算法 自己也是自己的祖先 倍增: f a ( i , j ) fa(i, j) f a ( i , j ) 表示從i開始,向上走 2 j 2^j 2 j 步走到的點 j = 0,走到父節(jié)點 j 0,分兩步走,先走到 2 j ? 1 2^{j-1} 2 j ? 1 步再走 2 j ? 1 2^{

    2024年02月13日
    瀏覽(26)
  • 第三章 圖論 No.9有向圖的強(qiáng)連通與半連通分量

    第三章 圖論 No.9有向圖的強(qiáng)連通與半連通分量

    連通分量是無向圖的概念,yxc說錯了,不要被誤導(dǎo) 強(qiáng)連通分量:在一個有向圖中,對于分量中的任意兩點u,v,一定能從u走到v,且能從v走到u。強(qiáng)連通分量是一些點的集合,若加入其他點,強(qiáng)連通分量中的任意兩點就不能互相遞達(dá) 半連通分量:在一個有向圖中,對于分量中

    2024年02月13日
    瀏覽(17)
  • 第三章 圖論 No.5最小生成樹之虛擬源點,完全圖與次小生成樹

    第三章 圖論 No.5最小生成樹之虛擬源點,完全圖與次小生成樹

    虛擬源點:1146. 新的開始 1146. 新的開始 - AcWing題庫 與一般的最小生成樹問題不同,本題需要在建立電站的電井之間建立電網(wǎng),在兩個電站之間建立電網(wǎng)需要花費(fèi)金額,可以看成一條具有權(quán)值的邊 但是建立電網(wǎng)的前提是:其中一個電井需要建立電站,建立電站也需要費(fèi)用 已經(jīng)

    2024年02月14日
    瀏覽(24)
  • 第三章 圖論 No.3 flody之多源匯最短路,傳遞閉包,最小環(huán)與倍增

    第三章 圖論 No.3 flody之多源匯最短路,傳遞閉包,最小環(huán)與倍增

    flody的四個應(yīng)用: 多源匯最短路 傳遞閉包 找最小環(huán) 恰好經(jīng)過k條邊的最短路 倍增 多源匯最短路:1125. 牛的旅行 1125. 牛的旅行 - AcWing題庫 直徑概念:同一連通塊中,兩個距離最遠(yuǎn)的點之間的距離 如何求直徑?由于圖中存在著兩個連通塊,所以直接對全圖做一個flody,就能更

    2024年02月14日
    瀏覽(27)
  • 第三章 圖論 No.2單源最短路之虛擬源點,狀壓最短路與最短路次短路條數(shù)

    第三章 圖論 No.2單源最短路之虛擬源點,狀壓最短路與最短路次短路條數(shù)

    dp是特殊的最短路,是無環(huán)圖(拓?fù)鋱D)上的最短路問題 1137. 選擇最佳線路 1137. 選擇最佳線路 - AcWing題庫 對于每組測試數(shù)據(jù),該重置的數(shù)據(jù)要重置,我沒有重置idx,導(dǎo)致TLE 處理反向建圖,還有一種擴(kuò)展做法:虛擬源點 設(shè)置虛擬源點,與每個起點之間連接邊權(quán)為0的邊 原問題

    2024年02月14日
    瀏覽(27)
  • 第三章 搜索與圖論(二)(最短路)

    第三章 搜索與圖論(二)(最短路)

    1、對于稠密圖,由于樸素版的dijkstra算法與邊數(shù)無關(guān)使用這種算法的復(fù)雜度較低。稀疏圖用堆優(yōu)化版的算法;單源最短路中存在負(fù)權(quán)邊用SPFA 算法通常較好;多源用floyd算法; ?難點:如何建圖,抽象為最短路問題。 由于稠密圖用這種算法,鄰接矩陣存圖,注意把g初始化為

    2024年02月21日
    瀏覽(17)
  • 第三章 搜索與圖論(二)——最短路問題

    第三章 搜索與圖論(二)——最短路問題

    源點表示起點,匯點表示終點 一些認(rèn)識: m和 n 2 n^2 n 2 一個級別是稠密圖,m和n一個級別是稀疏圖 最短路問題不區(qū)分有向圖與無向圖,因為無向圖是一種特殊的有向圖,能解決有向圖的最短路問題,就能解決無向圖的最短路問題 起點確定,終點是除起點外的其他點 默認(rèn)n表示

    2024年02月13日
    瀏覽(36)
  • C++算法之旅、06 基礎(chǔ)篇 | 第三章 圖論

    常用代碼模板3——搜索與圖論 - AcWing 盡可能往深處搜,遇到葉子節(jié)點(無路可走)回溯, 恢復(fù)現(xiàn)場繼續(xù)走 數(shù)據(jù)結(jié)構(gòu):stack 空間:需要記住路徑上的點, (O(h)) 。 ? BFS使用空間少; 無最短路 性質(zhì) 每個DFS一定對應(yīng)一個 搜索樹 ;要考慮用什么 順序 遍歷所有方案;DFS就是遞

    2024年02月10日
    瀏覽(35)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包