Written with StackEdit.

Description

小\(F\) 的学校在城市的一个偏僻角落,所有学生都只好在学校吃饭。学校有一个食堂,虽然简陋,但食堂大厨总能做出让同学们满意的菜肴。当然,不同的人口味也不一定相同,但每个人的口味都可以用一个非负整数表示。由于人手不够,食堂每次只能为一个人做菜。做每道菜所需的时间是和前一道菜有关的,若前一道菜的对应的口味是\(a\),这一道为\(b\),则做这道菜所需的时间为\((a|b)-(a \&b)\),而做第一道菜是不需要计算时间的。学生数目相对于这个学校还是比较多的,吃饭做菜往往就会花去不少时间。因此,学校食堂偶尔会不按照大家的排队顺序做菜,以缩短总的进餐时间。虽然同学们能够理解学校食堂的这种做法,不过每个同学还是有一定容忍度的。也就是说,队伍中的第\(i\) 个同学,最多允许紧跟他身后的\(B_i\) 个人先拿到饭菜。一旦在此之后的任意同学比当前同学先拿到饭,当前同学将会十分愤怒。因此,食堂做菜还得照顾到同学们的情绪。现在,小\(F\) 想知道在满足所有人的容忍度这一前提下,自己的学校食堂做完这些菜最少需要多少时间。

Input

第一行包含一个正整数\(C\),表示测试点的数据组数。每组数据的第一行包含一个正整数\(N\),表示同学数。每组数据的第二行起共\(N\)行,每行包含两个用空格分隔的非负整数\(T_i\)和\(B_i\),表示按队伍顺序从前往后的每个同学所需的菜的口味和这个同学的忍受度。每组数据之间没有多余空行。

Output

包含\(C\)行,每行一个整数,表示对应数据中食堂完成所有菜所需的最少时间。

Sample Input

2

5

5 2

4 1

12 0

3 3

2 2

2

5 0

4 0

Sample Output

16

1

HINT

对于第一组数据:同学1允许同学2或同学3在他之前拿到菜;同学2允许同学3在他之前拿到菜;同学3比较小气,他必须比他后面的同学先拿菜…… 一种最优的方案是按同学3、同学2、同学1、同学4、同学5做菜,每道菜所需的时间分别是0、8、1、6及1。

[数据规模和约定]

对于\(30\%\)的数据,满足\(1 ≤ N ≤ 20\)。

对于\(100\%\)的数据,满足\(1 ≤ N ≤ 1,000,0 ≤ T_i ≤ 1,000,0 ≤ B_i ≤ 7,1 ≤ C ≤ 5\)。

存在\(30\%\)的数据,满足\(0 ≤ B_i ≤ 1\)。

存在\(65\%\)的数据,满足\(0 ≤ B_i ≤ 5\)。

存在\(45\%\)的数据,满足\(0 ≤ T_i ≤ 130\)。

Solution

  • \(n\)较小,考虑状压\(dp\).
  • 令\(f(i,j,k)\)表示前\(i-1\)个人吃了饭,\(i\)及\(i\)之后的属于集合\(j\)的人也吃了饭,最后一个吃饭的人为\(i+k\)时所用的花费.
  • 转移时,如果\(j\&1=1\),说明\(i\)已经吃了饭.直接转移到\(f(i+1,j>>1,k)\),不需要额外花费.
  • 否则,枚举下一个吃饭的人是\(i+l\),满足\(i+l\)还没有吃过饭.
  • 这样就只能在\(l\geq0\)内找,因为状态定义满足\(i\)之前的都吃过饭.
  • 还要满足\(l\notin j\),以及满足\([i,i+l-1]\)内的容忍度限制,即可完成转移.
  • 答案为前\(n\)个人均吃了饭,且后面没有人再吃饭的最小花费,即\(min\{f(n+1,0,k)\}\).
  • 注意到\(k\)可能为负数.所以需要将\(k\)平移为\(k+8\).

\((a|b)-(a \&b)=(a\)^\(b)\).

#include<bits/stdc++.h>
#define f(i,j,k) F[i][j][k+8]
#define inf 0x3f3f3f3f
#define st f(i,j,k)
using namespace std;
typedef long long LoveLive;
inline int read()
{
int out=0,fh=1;
char jp=getchar();
while ((jp>'9'||jp<'0')&&jp!='-')
jp=getchar();
if (jp=='-')
{
fh=-1;
jp=getchar();
}
while (jp>='0'&&jp<='9')
{
out=out*10+jp-'0';
jp=getchar();
}
return out*fh;
}
const int MAXN=1e3+10;
int n,ans;
int t[MAXN],b[MAXN];
int F[MAXN][257][17];
inline int calc(int x,int y)//上一个恰饭的人是x,当前恰饭的人是y.计算花费.
{
return x==0? 0:t[x]^t[y];
}
// a|b - a&b = a^b
int main()
{
int T=read();
while(T--)
{
memset(F,inf,sizeof F);
n=read();
for(int i=1; i<=n; ++i)
t[i]=read(),b[i]=read();
f(1,0,-1)=0;
int S=1<<8;
for(int i=1; i<=n; ++i)
for(int j=0; j<S; ++j)
for(int k=-8; k<=7; ++k)
if(st<inf)
{
#define st1 f(i+1,j>>1,k-1)
#define st2 f(i,j+(1<<l),l)
if(j&1)
st1=min(st1,st);
else
{
int lim=inf;
for(int l=0; l<=7; ++l)
if(!(j&(1<<l)))//注意括号
{
if(i+l>lim)
break;
lim=min(lim,i+l+b[i+l]);
st2=min(st2,st+calc(i+k,i+l));
}
}
}
ans=inf;
for(int k=-8; k<=7; ++k)
ans=min(ans,f(n+1,0,k));
printf("%d\n",ans);
}
return 0;
}

bzoj 1226 学校食堂Dining的更多相关文章

  1. [SDOI2009][BZOJ 1226]学校食堂

    Description 小F 的学校在城市的一个偏僻角落,所有学生都只好在学校吃饭.学校有一个食堂,虽然简陋,但食堂大厨总能做出让同学们满意的菜肴.当然,不同的人口味也不一定相同,但每个人的口味都可以 ...

  2. bzoj [SDOI2009]学校食堂Dining

    感觉这个状压dp比较难想.. dp[ i ][ s ][ k ] 表示前i - 1个都排好了, 从i开始的7个的取没取的状态为s, 且最后一个相对i的位置为k的最少花费. 状态转移方程 if(s &a ...

  3. BZOJ 1226 学校食堂(状压DP)

    状压DP f(i,j,k)表示前i−1个人已经吃了饭,且在i之后的状态为j的人也吃了饭(用二进制表示后面的状态),最后吃的那个人是i之后的第k个 (注意k可以是负数) 然后 如果j&1=1那么 ...

  4. BZOJ 1226: [SDOI2009]学校食堂Dining

    1226: [SDOI2009]学校食堂Dining Time Limit: 10 Sec  Memory Limit: 259 MBSubmit: 730  Solved: 446[Submit][ ...

  5. BZOJ-1226 学校食堂Dining 状态压缩DP

    1226: [SDOI2009]学校食堂Dining Time Limit: 10 Sec Memory Limit: 259 MB Submit: 588 Solved: 360 [Submit][ ...

  6. 【BZOJ1226】[SDOI2009]学校食堂Dining 状压DP

    [BZOJ1226][SDOI2009]学校食堂Dining Description 小F 的学校在城市的一个偏僻角落,所有学生都只好在学校吃饭.学校有一个食堂,虽然简陋,但食堂大厨总能做出让同学们满 ...

  7. 1226: [SDOI2009]学校食堂Dining - BZOJ

    Description 小F 的学校在城市的一个偏僻角落,所有学生都只好在学校吃饭.学校有一个食堂,虽然简陋,但食堂大厨总能做出让同学们满意的菜肴.当然,不同的人口味也不一定相同,但每个人的口味都可以 ...

  8. bzoj 1226 [SDOI2009]学校食堂Dining(状压DP)

    Description 小F 的学校在城市的一个偏僻角落,所有学生都只好在学校吃饭.学校有一个食堂,虽然简陋,但食堂大厨总能做出让同学们满意的菜肴.当然,不同的人口味也不一定相同,但每个人的口味都可以 ...

  9. [SDOI2009]学校食堂Dining

    题目描述 小F 的学校在城市的一个偏僻角落,所有学生都只好在学校吃饭.学校有一个食堂,虽然简陋,但食堂大厨总能做出让同学们满意的菜肴.当然,不同的人口味也不一定相同,但每个人的口味都可以用一个非负整数 ...

随机推荐

  1. Firebug入门指南(转)

    本文转自:http://www.ruanyifeng.com/blog/2008/06/firebug_tutorial.html 作者: 阮一峰 日期: 2008年6月 8日 据说,对于网页开发人员 ...

  2. 一键配置IP地址脚本

    #/bin/bash NETPWD='/etc/sysconfig/network-scripts/' read -p "please enten net num(1,2,3,4) : &q ...

  3. React Native之持久化存储(AsyncStorage、react-native-storage)的使用

    AsyncStorage是一个简单的.异步的.持久化的Key-Value存储系统,它对于App来说是全局性的.这是官网上对它的介绍.可以知道,这个asyncstorage也是以键值对的形式进行存储数据 ...

  4. SSL证书是“盾牌“还是”鸡肋“?

    德国联邦安全与IT办公室(BSI,职能相当于美国的国家安全与信息技术局)近日发布公告警告:网络攻击者冒充其发布了“关于Meltdown与Spectre攻击信息”的垃圾邮件,该邮件中包含指向修复补丁的页 ...

  5. nodejs 设计模式

    1 . 单例模式 顾名思义,单例就是保证一个类只有一个实例,实现的方法是,先判断实例是否存在,如果存在则直接返回,若不存在,则创建实例对象,并将实例对象保存在静态变量中,当下次请求时,则可以直接返回这 ...

  6. Hyper:基于Hypervisor的容器化解决方案

    近日,初创公司HyperHQ发布了他们的开源项目Hyper,Hyper是一个可以在hypervisor上运行Docker镜像的引擎,它融合了Docker容器和虚拟机的优点,旨在打造一个性能更好.更安全 ...

  7. 绘制三角形(sass)

    绘制三角形 /// draw triangle/// @param {type} $type [''] - triangleUp triangleDown triangleLeft triangleR ...

  8. 【Demo】HTML5获取地理位置

    HTML5获取地理位置简单实例 实例1--获取地理位置的经纬度: <!DOCTYPE html> <html> <head>  <meta charset=& ...

  9. 四 web爬虫,scrapy模块标签选择器下载图片,以及正则匹配标签

    标签选择器对象 HtmlXPathSelector()创建标签选择器对象,参数接收response回调的html对象需要导入模块:from scrapy.selector import HtmlXPa ...

  10. Isilon

    Isilon编辑 本词条缺少信息栏,补充相关内容使词条更完整,还能快速升级,赶紧来编辑吧! 美国Isilon公司是全球群集存储系统的主要供应商,是该领域的领导者.总部位于美国华盛顿州的西雅图.创建于2 ...