沒啥營養的狀壓dp。
題意見洛谷。(以下用\(s\)表示題目中的\(k\))先預處理出\(cnt_=\sum\limits_^[s_k=i][s_=j]\)。然後設位置\(i\)是\(id_i\)號訊號站,推一波\(\sum\)算出每個位置對答案的貢獻:
\[\beginans&=\sum_^m\sum_^mcnt_(j-i)+\sum_^m\sum_^cnt_s(i+j)\\&=\sum_^m-i\sum_^mcnt_+\sum_^mi\sum_^cnt_+s\sum_^mi\sum_^cnt_+s\sum_^mi\sum_^mcnt_\\&=\sum_^mi\left(\sum_^m\left(s\cdot cnt_-cnt_\right)+\sum_^\left(s\cdot cnt_+cnt_\right)\right)\end
\]然後就有乙個很顯然的基於位置的狀壓dp了。設\(dp_\)表示考慮到第\(|i|\)位,前\(|i|\)位的訊號站編號集合為\(i\)時的最小總貢獻。邊界:\(dp_=0\),目標:\(dp_\)。
令\[val_=\sum_\left(s\cdot cnt_-cnt_\right)+\sum_\left(s\cdot cnt_+cnt_\right)
\]它可以通過先預處理\(\forall i\in[1,m],val_\),剩下的拎出來乙個\(\mathrm\)來\(\mathrm o(1)\)轉移來求出,時間複雜度\(\mathrm o(2^mm)\)。
那麼狀態轉移方程:
\[dp_=\min_\!\left\}+|i|val_}\right\}
\]如此,總時空複雜度皆為\(\mathrm o(2^mm)\)。
至此是我在考場上的做法,\(80\mathrm\),因為空間會**,乙個\(val\)陣列大概是\(700\)多\(\mathrm\)。考慮優化。
注意到轉移方程裡的\(val_}\),不難發現若\(x\in y\),那麼\(val_\)是不可能被用到的。這樣一來,若只存會被用到的,空間立刻減半,能過。可轉移性也很顯然。實現也很簡單,只需要讓每個\(j\)的末\(i-1\)位原封不動,其他的位拆出來右移\(1\)位,再拼起來即可。
關於卡空間,還有很多的奇技淫巧可以把空間卡的很小很小,不過研究這個也沒啥意義了(
**(開洛谷自帶o2才能過(似乎洛谷機+o2=ccf機?)):
#includeusing namespace std;
const int inf=int_max;
int lowbit(int x)
const int m=23;
int n,m,s;
int cnt[m][m];
int val[m][1<>n>>m>>s;
int las;
for(int i=1;i<=n;i++)
for(int i=0;i>1)]=val[i][(x&(1<>1)]+(s*cnt[i][y]+cnt[y][i])-(s*cnt[y][i]-cnt[i][y]);//遞推
} }for(int i=1;i<1<>1)]);//轉移方程
} }cout
}
洛谷P2661 資訊傳遞
有n個同學 編號為1到n 正在玩乙個資訊傳遞的遊戲。在遊戲裡每人都有乙個固定的資訊傳遞物件,其中,編號為i的同學的資訊傳遞物件是編號為ti同學。遊戲開始時,每人都只知道自己的生日。之後每一輪中,所有人會同時將自己當前所知的生日資訊告訴各自的資訊傳遞物件 注意 可能有人可以從若干人那裡獲取資訊,但是每...
洛谷 P2661 資訊傳遞
有 n個同學 編號為1到 n 正在玩乙個資訊傳遞的遊戲。在遊戲裡每人都有乙個固定的資訊傳遞物件,其中,編號為 i的同學的資訊傳遞物件是編號為 ti同學。遊戲開始時,每人都只知道自己的生日。之後每一輪中,所有人會同時將自己當前所知的生日資訊告訴各自的資訊傳遞物件 注意 可能有人可以從若干人那裡獲取資訊...
洛谷 P2661 資訊傳遞
有 nn n 個同學 編號為 11 1 到 nn n 正在玩乙個資訊傳遞的遊戲。在遊戲裡每人都有乙個固定的資訊傳遞物件,其中,編號為 ii i 的同學的資訊傳遞物件是編號為 tit iti 的同學。遊戲開始時,每人都只知道自己的生日。之後每一輪中,所有人會同時將自己當前所知的生日資訊告訴各自的資訊傳...