BZOJ 刷题记录 PART 6

【BZOJ2709】水的二分加验证。可是好像被读入萎到了。。。

【BZOJ3229】强大的算法见此。被机房的一堆大神“推荐”。于是被坑了。。。写了一个下午。。。

【BZOJ3631】这道题给我的启发是:要多想想算法。

開始一直在打树链剖分,打到一半忽然在众神犇的提(bi)示(shi)下。发现有O(N)的方法。试想:假设要支持区间改动(加减),最后再查询,能够用什么方法?固然,线段树和树状数组等等都能够,可是最好的显然是类似于前缀和的思想。比方在L~R加上一个数,能够再L处+K。在R+1处-K。

然后最后的时候从头到尾扫过去、累加就可以。

那么这道题实际上是在树上做这个类似的操作。当然,求LCA的时候要用tarjan,否则效率又变回去了。

下面是代码。wri是为了调整,最后输出的是wri和sum的和。

void bfs(int k)
{
  for (int i=1;i<n;i++)
  {
    int x=opt[i],y=opt[i+1];
    sum[ans[i]]-=2;
    sum[x]++;sum[y]++;
    wri[y]--;wri[ans[i]]++;
  }
  int h=0,t=1;q[1]=1;
  while (h<t)
  {
    int now=q[++h];
    for (int i=end[now];i;i=a[i].next)
    {
      int go=a[i].go;if (go==fa[now]) continue;
      q[++t]=go;
    }
  }
  for (int j=t;j;j--)
  {
    int k=q[j];
    sum[fa[k]]+=sum[k];
  }
}

【BZOJ3609】打表找规律。据说是版权问题?就不说了。

【BZOJ1212】啊哈哈哈。又被我DP使过去啦!

【BZOJ2823&1666&1667】曾经查来的题解。。。

好像是谁的论文来着。

初始圆为1,2作为直径的圆。

For
i=2 to n

If
i不在当前圆内 then

   把当前圆设为以1,i为直径的圆

    For
j=2 to i-2

    If
j不在当前圆内 then

    把当前圆设为以j,i为直径的圆{确定初始圆}

        For
k=1 to j-1

        If
k不在当前圆内 then

           把当前圆设为I,j,k三点确定的圆。{确定三点确定的圆}

输出当前圆

【BZOJ1802】真的是好题。我们先来考虑在开头的时候放的尽量的少。

①假设有两个相邻的红格。那么我能够在放好后之后到达不论什么一个点!于是第一问就是0。至于第二问。找出全部相邻的红格,直接用DP往左右扫。

 for (int i=k-1;i;i--)
    f[i]=min(f[i],f[i+1]+f[i+2]);

②否则必须在偶数格放棋子。扫一遍就可以。

for (i=2;i<n;i++)
    if (a[i]&a[i+1]) {flag=1;break;}
  if (!flag)
  {
    for (i=2;i<n;i++)
      if (!(i&1)) a[i]?ans2++:ans1++;
    printf("%lld\n%lld",ans1,ans2);
    return 0;
  }
  memset(f,60,sizeof(f));
  for (i=1;i<=n;i++) if (a[i]) f[i]=1;
  for (i=2;i<n;i++)
    if (a[i]&a[i+1]) bfs_left(i),bfs_right(i+1);
  for (i=2;i<n;i++)
    if (!(i&1)) ans2+=f[i];

【BZOJ3574】题解传送门(跪SYC大爷!)

【BZOJ1873】写的天昏地暗!

我认为有必要贴一下代码。

#include<cstdio>
#include<cstring>
#include<map>
#include<string>
#define N 20005
#define P 41
using namespace std;
map<string,int>pre;
const char Num[11][P]={"","","","killing spree","dominating","mega kill",
"unstoppable","wicked sick","monster kill","godlike","beyond godlike"};
const char Wri[11][P]={"","","","is on a killing spree!","is dominating!",
"has a mega kill!","is unstoppable!","is wicked sick!","has a monster kill!",
"is godlike!","is beyond godlike. someone kill him!"};
char a[P],b[P],Time[P],ch[P];
int belong[N],num[N],kill[N],last[N],death[2];
int A,B,now_Time,ok_kill,ALL,n,i,Q;
bool check()
{
  A=pre[a];B=pre[b];
  return A&&B&&A!=B;
}
void get_Time(){now_Time=(Time[0]*10+Time[1])*60+Time[3]*10+Time[4];}
void First()
{
  if (A==B) {printf("%s has killed himself.\n",a);return;}
  if (!ok_kill) {printf("%s has been killed by %s.\n",b,a);return;}
  if (num[B]>=3) {printf("%s has just ended %s's %s.\n",a,b,Num[num[B]<=10?

num[B]:10]);num[B]=0;return;}
  printf("%s pawned %s's head.\n",a,b);num[B]=0;
  if (ok_kill&&!ALL) ALL=1,printf("%s just drew first blood.\n",a);
}
void Second()
{
  if (!ok_kill) return;
  num[A]++;
  if (num[A]>=3)
  {
    if (num[A]<=10) printf("%s %s\n",a,Wri[num[A]]);
    else printf("%s %s\n",a,Wri[10]);
  }
}
void Third()
{
  if (!ok_kill) return;
  if (kill[A]&&now_Time<=last[A]+10)
  {
    if (kill[A]==1) printf("%s just got a Double Kill!\n",a);
    else printf("%s just got a Triple Kill!\n",a);
  }
  else kill[A]=0;
  kill[A]++;last[A]=now_Time;
}
void Fourth()
{
  if (!ok_kill) return;
  int now=belong[B];death[now]++;death[now^1]=0;
  if (death[now]>=5)
    printf("The %s is OWNING!\n",!now?"Scourge":"Sentinel");
}
int main()
{
  freopen("1873.out","w",stdout);
  scanf("%d",&n);
  for (i=1;i<=n;i++)
    scanf("%s%d",a,&belong[i]),pre[a]=i;
  scanf("%d",&Q);ALL=0;
  while (Q--)
  {
    scanf("%s%s%s%s%s%s",Time,b,ch,ch,ch,a);
    ok_kill=check();get_Time();
    First();Second();Third();Fourth();
  }
  return 0;
}

【BZOJ1925*】至今还认为奇怪的DP(递推、组合数)。有空去看看。

【BZOJ1819】好题目!

用dfs序的性质。树状数组维护,还要求LCA。開始忘了怎么在dfs序的树状数组中维护某个点的子树的信息,去问了RZZ,后来发现根本就是傻X问题啊。

时间: 2024-08-05 11:16:14

BZOJ 刷题记录 PART 6的相关文章

BZOJ 刷题记录 PART 4

[BZOJ1143]CTSC的题目...先用floyed传递闭包,然后直接上匈牙利算法. [BZOJ1452]从未写过的二维树状数组.好像很简单.. struct two_bit { int f[305][305]; inline void add(int x,int z,int A) { for (;x<=n;x+=L(x)) for (int y=z;y<=m;y+=L(y)) f[x][y]+=A; } inline int ask(int x,int z) { int ans=0; f

BZOJ 刷题记录 PART 5

拖了好久才写的. [BZOJ2821]接触分块大法.这道题略有点新颖.首先我们先分块,然后统计每块中每个数出现的个数. 下面是联立各个方块,预处理出第I个方块到第J个方块出现正偶数次数的个数. for (i=1;i<=s;i++) { for (j=i;j<=s;j++) { sum[i][j]=sum[i][j-1]; for (k=a[j].l;k<=a[j].r;k++) { temp[data[k]]++; if (!(temp[data[k]]&1)) sum[i][j

BZOJ 刷题记录 PART 1

作者 : Dolphin 原文地址:http://blog.csdn.net/qingdujun/article/details/27109035 一.实体完整性定义 [例1]将Student表中的Sno属性定义为码. CREATE TABLE Student ( Sno CHAR(10) PRIMARY KEY, /*在列定义主码*/ Sname CHAR(20) NOT NULL, Sage SMALLINT ); 或者: CREATE TABLE Student ( Sno CHAR(10

BZOJ 刷题记录 PART 2

[前言]最近感觉状态不错.做题几乎不看题解了.(一群大牛(FZ&WCY)在旁边喷:你刷水题有意思!)但是至少这也是一种进步吧.特别是权限题中有很多思维题. [BZOJ1055]就是一个简单的区间DP.重要代码: for (l=2;l<=L;l++) for (i=1;i<=L-l+1;i++) { j=i+l-1; for (k=0;k<4;k++) for (cut=i;cut<j;cut++) for (p=0;p<4;p++) if (f[i][cut][p])

BZOJ 刷题记录 PART 3

[前言]还是强调要少看题解. [BZOJ1090]简单的区间DP.值得注意的是:在压缩的时候,如果是10个A压缩,那么化成(10)A后有5个字符而不是4个!(我在这里被坑了好长时间!)以下是核心代码: for (len=2;len<=L;len++) for (i=1;i<=L-len+1;i++) { j=i+len-1; for (k=i;k<j;k++) f[i][j]=min(f[i][j],f[i][k]+f[k+1][j]); for (l=1;l<=len/2;l++

[2015.6.28] OI刷题记录

FZSZOJ刷题记录: 1051 砝码称重: DP 多重背包 1058 liqeuer: 序列DP 1061 挖地雷:DP,注意需要倒过来做DP,同时记录路径. 1059 Number:DP 1054 数塔问题:同数字三角形,普通DP 1390 等式问题:爆搜,枚举每个+号或-号的位置 1006 中位数:维护大根堆+小根堆,每次插入调整 1005 Cube Stacking:并查集维护当前在第几个和当前集合的高度,并查集变种. 1073 DNA分子的最佳比对:序列DP 1110 奖学金:傻逼题,

首师大附中科创教育平台 我的刷题记录(3)

首师大附中科创教育平台我的刷题记录(给大家刷11--15题吧) 仅供同学们参考,禁止抄袭!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! #include<iostream> #include<math.h> using namespace std; int main() { int x,y; cin>>x; y=abs(x+2); cout<<x*x-y+5<<endl; return 0; } 绝对值函数 #include

【BZOJ做题记录】07.07~?

在NOI一周前重开一个坑 最后更新时间:7.07 11:26 7.06 下午做的几道CQOI题: BZOJ1257: [CQOI2007]余数之和sum:把k mod i写成k-k/i*i然后分段求后面的部分就好了 BZOJ1258: [CQOI2007]三角形tri:在草稿纸上按照位置和边找一下规律就好了 BZOJ1260: [CQOI2007]涂色paint:简单的区间DP BZOJ1303: [CQOI2009]中位数图:小于中位数的改为-1大于的改为1,算一算前缀和然后哈希一下乘一乘就好

首师大附中科创教育平台 我的刷题记录(7)

首师大附中科创教育平台我的刷题记录(这次给大家刷多一点,31--40题吧) 仅供同学们参考,禁止抄袭!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! #include<iostream> using namespace std; int main() { int n; cin>>n; if(n%4==0&&n%100!=0||n%400==0) cout<<"yes"<<endl; else cout&