zoukankan      html  css  js  c++  java
  • Fair Photography

    题目大意:

    给出直线上N个点的位置和颜色(0或1),求最大的区间,使得区间内0的个数大于等于1的个数且0的个数减去1的个数为偶数。

    解题过程:

    1.先贴个lsdsjy大牛的线段树的做法:http://www.cnblogs.com/lsdsjy/p/4032614.html

    2.这题一个非常巧妙的转换是:由于0的个数减去1的个数为偶数,那么区间内的点的个数只能是偶数,这样只要枚举左开右闭区间

    (L,R], R和L位置的奇偶性相同。 所以只要分2次做,奇数位的和偶数位的单独拿出来。

    下面仅讨论L,R都是偶数的情况。

    用A[i]表示前i个数1有多少个,B[i]表示前i个数0有多少。

    一个区间(L,R]符合要求必须满足A[R]-A[L]>=B[R]-B[L]  ->  A[R]-B[R] >= A[L]-B[L] 

    令K[i]=A[i]-B[i] ->  K[R] >= K[L]

    方法一(单调队列):

    如果一个有K[i],K[j]满足i<j && K[i]<=K[j] 那么选取区间的L端点的时候肯定是选i比较优

    所以可以维护一个单调队列,只有当新的K[i]<K[tail] 的时候 才加入队列。

    然后枚举右端点R,只要在单调队列中二分找到一个最小的i,满足K[i]<=K[R],那么以R为右端点的最优区间就是(i,R].

    方法二(动态规划):

    这种方法不必分奇偶讨论,非常巧妙.

    F[i]表示满足K[t]=i 的最小的t. g[i]=min{f[i],f[i-2],f[i-4]....}. 因为每次相差的都是二,可以保证0,1的个数奇偶性相同

    枚举右端点R,如果g[K[R]]<R,那么以R为右端点的最优区间就是( g[K[R]] , R] .

  • 相关阅读:
    Linux下redis的安装
    python 文档
    Asp.net 高性能 Sqlite ORM 框架之 sqliteSugar
    程序整理网
    第十章:更多
    第九章:高级应用举例
    第八章:简单应用举例(2)
    第八章:简单应用举例(1)
    第七章:Mapping插件
    第六章:加载或保存JSON数据
  • 原文地址:https://www.cnblogs.com/vb4896/p/4038561.html
Copyright © 2011-2022 走看看