(状压dp)[SDOI2009] 学校食堂 (抽风版)

[SDOI2009]学校食堂

一道朴实无华经典的练习抄题解文本替换和状压dp的题

link

题意

苏联高级女特工那艺娜说过“吃饱了就会不饿”,所以据此我们能得知不吃饱就会饿。学校食堂为了使时间最小可以调整排队学生的顺序,学生也不是软柿子也有忍耐限度,仅允许后面0~7人比他先打到饭。而食堂的菜全部新鲜现炒且只有一个师傅,所以每次只能为一位同学炒菜。由于两道菜可能串味,令相邻两道菜的美味度为 \(a\)\(b\),则炒后者所需要时间为 \((a ~or~ b)-(a ~and~ b)\)。求满足所有学生忍耐限度的时间最小值。

思路

有后效性所有首先排除动规。 处在状压dp板块考虑进行状压dp。观察到忍耐度 \(b\) 范围小且与每个人联系紧密,可以作为状态。本题有后效性,就需巧妙设计状态使其没有后效性。一个简单的做法,苦思冥想许久后打开题解做做阅读理解便能通过本题。
首先我们能知道 \(a ~or~ b\) 求的是 \(a\)\(b\) 二进制下的并, \(a ~and~ b\) 求的是二进制下 \(a\)\(b\) 的交。并减去交得到的就是 \(a\)\(b\) 不同的位的并,与异或定义相同,故能简化运算,每道菜的时间即为 \(a ~xor~ b\)
增设第三维为上一个打饭的同学在当前同学的后第几个,易知其取值范围为 \([-8,7]\),由于数组没有负的下标,可以使用宏定义简化下标的范围。
当当前同学打完饭,则该同学以后的顺序与其无关,故可以更新其后同学的状态

\[ f[i+1][j>>1][dd(k-1)]=min(f[i][j][dd(k)]) \]

当当前同学没打完饭,枚举其后谁先吃饭。注意及时更新最大右端点。

\[ f[i][j|(1<<l)][dd(l)]=min(f[i][j|(1<<l)][dd(l)],x+(i+k!=0)*(t[i+k]\text{^}t[i+l])) \]

posted @ 2025-08-09 15:39  _dlwlrma  阅读(7)  评论(0)    收藏  举报