GDINOJ1044--狀態(tài)壓縮動(dòng)態(tài)規(guī)劃

無(wú)論多忙都好艘刚,每日都要進(jìn)行數(shù)學(xué)思維和計(jì)算機(jī)思維的鍛煉,才能讓自己做事高效且思維敏捷姐霍。


題目(GDINOJ)

http://114.215.99.34/#/enter/problem?pid=1044
春游的時(shí)間到了蕊玷,CC想要利用這個(gè)難得的好時(shí)間去旅游应媚。
CC有N個(gè)想要去的旅游景點(diǎn)珊泳,他想要在這個(gè)寒假全部都去玩一次鲁冯,經(jīng)過(guò)他的調(diào)查,他已經(jīng)得到了任何兩個(gè)旅游景點(diǎn)之間的路費(fèi)色查。所以他想讓你幫他設(shè)計(jì)一條旅行路線薯演,使得最終的費(fèi)用最小。

分析

這是一個(gè)很經(jīng)典的TSP問(wèn)題了秧了,NP難的一個(gè)問(wèn)題涣仿。因?yàn)闀r(shí)間復(fù)雜度是N!,所以這里輸入上限是20示惊。雖然只有20個(gè)城市,但是時(shí)間復(fù)雜度依然相當(dāng)高愉镰,常規(guī)算法依然十分耗時(shí)米罚。(現(xiàn)在已經(jīng)有很好地啟發(fā)式算法的方案來(lái)解決了,這里不展開(kāi)討論丈探,這里討論的是常規(guī)算法)

求解

我們采用動(dòng)態(tài)規(guī)劃來(lái)求解录择,動(dòng)態(tài)規(guī)劃最難的地方在于如何證明子問(wèn)題具有全局最優(yōu),狀態(tài)的定義和狀態(tài)轉(zhuǎn)移方程的設(shè)定碗降。當(dāng)然了隘竭,編程實(shí)現(xiàn)也不容易。

狀態(tài)定義

我們先尋求一下最優(yōu)解子結(jié)構(gòu)讼渊,我們先定義一個(gè)狀態(tài)dp(i,j)动看,其中i表示從旅行到了第i點(diǎn),j是一個(gè)集合爪幻,表示未旅行的點(diǎn)的集合菱皆。所以须误,狀態(tài)dp(i,j)就表示從起點(diǎn)開(kāi)始旅行到了第i點(diǎn),還有集合J的點(diǎn)沒(méi)有旅行的最少費(fèi)用仇轻。

狀態(tài)轉(zhuǎn)移

dp(i,j) = min( dp(i,j) , dp(i, j - k) + G[i][k]) (k 屬于集合k)京痢,狀態(tài)方程其實(shí)也比較容易理解,就是嘗試每一種未旅行的城市篷店,并且記錄下來(lái)祭椰。

實(shí)現(xiàn)細(xì)節(jié)
  1. 單純看轉(zhuǎn)移方程,時(shí)間復(fù)雜度是n!的。但是DP的核心是打表坤溃,所以記錄過(guò)的就不要再跑了格二。
  2. 如何來(lái)表示集合J呢?這里運(yùn)用了狀態(tài)壓縮的技巧臣淤,就是把城市用二級(jí)制來(lái)表示,這里注意爆內(nèi)存窃爷。
代碼
#include <string.h>
#include <math.h>

int F[30][30];

const int INF = 99999999 ;
const int MAX = (1<<20)+1 ;
int dp[21][MAX];
int dis[30][30] ;

int min(int a, int b) {
    return a<b?a:b ;
}
int n ;

int InitState() {
    int res = 0 ;
    for( int i = 1 ; i<=n ;i++ ) {
        res = res| (1<<(i-1));
    }
    return res ;
}

int GetState(int State, int des) {
    State = State^(1<<(des-1)) ;
    return State ;
}

void DP(int State, int des) {
    int& Temp = dp[des][State];
    if (Temp != INF)    return ;
    if( State == 0 ) {
        Temp = F[des][0] ;
        return ;
    } else {
        for( int i = 1 ; i<= n ;i++ ) {
            if( State & (1<<(i-1)) ) {
                int NewState = GetState(State,i);
                DP(NewState, i);
                Temp = min(Temp, dp[i][NewState]+F[des][i]);
            }
        }
    }
}

int main()
{
    // freopen("input.in","r",stdin);
    while(scanf("%d",&n) != EOF) {
        memset( dp , 0 , sizeof(dp) ) ;
        for( int i = 1 ; i<=n ;i++ ){scanf("%d",&F[0][i]); F[i][0] = F[0][i]; } 
        for( int i = 1 ; i<=n ; i++) {
            for( int j = 1 ; j<=n ; j++ ) {
                scanf("%d",&F[i][j]);
            }
        }
        int All = (1<<n) - 1;
        //init
        // printf("All: %d\n",All);
        for( int i = 0 ; i<=n ; i++ )
            for( int j = 0 ; j<=All ; j++)
                dp[i][j] = INF ;
        All = InitState();
        DP(All,0);
        printf("%d\n",dp[0][All]) ;
    }
    return 0;
}

感悟

雖然這題大二的時(shí)候就做過(guò)了邑蒋。。
我只是想試試步入了社會(huì)之后是否能沉下心來(lái)進(jìn)行數(shù)學(xué)按厘,算法和英語(yǔ)的訓(xùn)練呢医吊?堅(jiān)持它一年試試吧。逮京。卿堂。

2017-8-20

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市懒棉,隨后出現(xiàn)的幾起案子草描,更是在濱河造成了極大的恐慌,老刑警劉巖策严,帶你破解...
    沈念sama閱讀 212,454評(píng)論 6 493
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件穗慕,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡妻导,警方通過(guò)查閱死者的電腦和手機(jī)逛绵,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,553評(píng)論 3 385
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)倔韭,“玉大人术浪,你說(shuō)我怎么就攤上這事∈僮茫” “怎么了胰苏?”我有些...
    開(kāi)封第一講書(shū)人閱讀 157,921評(píng)論 0 348
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)份名。 經(jīng)常有香客問(wèn)我碟联,道長(zhǎng)妓美,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 56,648評(píng)論 1 284
  • 正文 為了忘掉前任鲤孵,我火速辦了婚禮壶栋,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘普监。我一直安慰自己贵试,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 65,770評(píng)論 6 386
  • 文/花漫 我一把揭開(kāi)白布凯正。 她就那樣靜靜地躺著毙玻,像睡著了一般。 火紅的嫁衣襯著肌膚如雪廊散。 梳的紋絲不亂的頭發(fā)上桑滩,一...
    開(kāi)封第一講書(shū)人閱讀 49,950評(píng)論 1 291
  • 那天,我揣著相機(jī)與錄音允睹,去河邊找鬼运准。 笑死,一個(gè)胖子當(dāng)著我的面吹牛缭受,可吹牛的內(nèi)容都是我干的胁澳。 我是一名探鬼主播,決...
    沈念sama閱讀 39,090評(píng)論 3 410
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼米者,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼韭畸!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起蔓搞,我...
    開(kāi)封第一講書(shū)人閱讀 37,817評(píng)論 0 268
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤胰丁,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后喂分,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體隘马,經(jīng)...
    沈念sama閱讀 44,275評(píng)論 1 303
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,592評(píng)論 2 327
  • 正文 我和宋清朗相戀三年妻顶,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片蜒车。...
    茶點(diǎn)故事閱讀 38,724評(píng)論 1 341
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡讳嘱,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出酿愧,到底是詐尸還是另有隱情沥潭,我是刑警寧澤,帶...
    沈念sama閱讀 34,409評(píng)論 4 333
  • 正文 年R本政府宣布嬉挡,位于F島的核電站钝鸽,受9級(jí)特大地震影響汇恤,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜拔恰,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 40,052評(píng)論 3 316
  • 文/蒙蒙 一因谎、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧颜懊,春花似錦财岔、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 30,815評(píng)論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至咸这,卻和暖如春夷恍,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背媳维。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,043評(píng)論 1 266
  • 我被黑心中介騙來(lái)泰國(guó)打工酿雪, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人侨艾。 一個(gè)月前我還...
    沈念sama閱讀 46,503評(píng)論 2 361
  • 正文 我出身青樓执虹,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親唠梨。 傳聞我的和親對(duì)象是個(gè)殘疾皇子袋励,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 43,627評(píng)論 2 350

推薦閱讀更多精彩內(nèi)容