题目描述 Description

给定正整数序列x1,..... , xn  。
(1)计算其最长递增子序列的长度s。
(2)计算从给定的序列中最多可取出多少个长度为s的递增子序列。
(3)如果允许在取出的序列中多次使用x1和xn,则从给定序列中最多可取出多少个长
度为s的递增子序列。

输入描述 Input Description

第1 行有1个正整数n,表示给定序列的长度。接
下来的1 行有n个正整数x1.....xn 。

输出描述 Output Description

第1 行是最长递增子序列的长度s。第2行是可取出的长度为s 的递增子序列个数。第3行是允许在取出的序列中多次使用x1和xn时可取出的长度为s 的递增子序列个数。

样例输入 Sample Input

4
3 6 2 5

样例输出 Sample Output

2
2
3

不得不吐槽codevs上面网络流24题好多数据都是很蛋疼的要输出方案又不给spj……鬼知道你数据是用哪种方案啊

啊这题还算正常

第一问LIS随便求

第二问拆点完S向所有x1连流量1费用0的边,所有x2向T连流量1费用0的边,所有x1向x2连流量1费用1的边。因为要表示有没有取这个点

对于所有a[i]<a[j]且i<j的,i2向j1连流量1费用0的边

然后跑最大费用。每次增广搞完如果答案是第一问的最长长度,那么ans++。

第三问就是第二问的建图与1和n有关的边的流量全改inf就对了

#include<cstdio>
#include<iostream>
#include<cstring>
#define LL long long
#define inf 0x3ffffff
#define S 0
#define T 1001
using namespace std;
inline LL read()
{
LL x=0,f=1;char ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
return x*f;
}
int n,ans,flow,cnt,tot;
int a[510];
int mn[510];
struct edge{int from,to,next,v,c;}e[500010];
int head[1010],dis[1010],q[1010],from[1010];
bool mrk[1010];
inline void ins(int u,int v,int w,int c)
{
e[++cnt].to=v;
e[cnt].v=w;
e[cnt].c=c;
e[cnt].from=u;
e[cnt].next=head[u];
head[u]=cnt;
}
inline void insert(int u,int v,int w,int c)
{
ins(u,v,w,c);
ins(v,u,0,-c);
}
inline int bsearch(int x)
{
int l=1,r=ans,s=0;
while(l<=r)
{
int mid=(l+r)>>1l;
if (mn[mid]<=x){s=mid;l=mid+1;}
else r=mid-1;
}
return s;
}
inline bool spfa()
{
for (int i=1;i<=T;i++)dis[i]=inf;
memset(mrk,0,sizeof(mrk));
int t=0,w=1;
dis[S]=0;q[0]=S;mrk[S]=1;
while (t!=w)
{
int now=q[t++];if (t==1005)t=0;
for (int i=head[now];i;i=e[i].next)
if (e[i].v&&dis[now]+e[i].c<dis[e[i].to])
{
dis[e[i].to]=dis[now]+e[i].c;
from[e[i].to]=i;
if (!mrk[e[i].to])
{
mrk[e[i].to]=1;
q[w++]=e[i].to;
if (w==1005)w=0;
}
}
mrk[now]=0;
}
if (dis[T]==inf)return 0;
return 1;
}
inline void mcf()
{
int x=inf;flow=0;
for (int i=from[T];i;i=from[e[i].from])
x=min(x,e[i].v);
for (int i=from[T];i;i=from[e[i].from])
{
e[i].v-=x;
e[i^1].v+=x;
flow+=x*e[i].c;
}
if (flow==-ans)tot++;
}
int main()
{
n=read();
for (int i=1;i<=n;i++)a[i]=read();
ans=1;mn[1]=a[1];
for (int i=2;i<=n;i++)
{
int fnd=bsearch(a[i]);
if (fnd==ans)mn[++ans]=a[i];
else mn[fnd+1]=a[i];
}
printf("%d\n",ans);
cnt=1;
for(int i=1;i<=n;i++)
{
insert(S,i,1,0);
insert(i+n,T,1,0);
insert(i,i+n,1,-1);
}
for (int i=1;i<=n;i++)
for (int j=i+1;j<=n;j++)
if (a[i]<=a[j])insert(i+n,j,1,0);
while (spfa())mcf();
printf("%d\n",tot);
memset(head,0,sizeof(head));
cnt=1;tot=0;
insert(S,1,inf,0);insert(S,n,inf,0);
insert(1+n,T,inf,0);insert(2*n,T,inf,0);
insert(1,1+n,inf,-1);insert(n,2*n,inf,-1);
for(int i=1;i<=n;i++)
{
insert(S,i,1,0);
insert(i+n,T,1,0);
insert(i,i+n,1,-1);
}
for (int i=1;i<n;i++)
for (int j=i+1;j<=n;j++)
if (a[i]<=a[j])
if (i!=1&&j!=n)insert(i+n,j,1,0);
else insert(i+n,j,inf,0);
while (spfa())mcf();
printf("%d\n",tot);
}

 

codevs1906 最长递增子序列问题的更多相关文章

  1. (转载)最长递增子序列 O(NlogN)算法

    原博文:传送门 最长递增子序列(Longest Increasing Subsequence) 下面我们简记为 LIS. 定义d[k]:长度为k的上升子序列的最末元素,若有多个长度为k的上升子序列,则 ...

  2. 最长公共子序列(LCS)和最长递增子序列(LIS)的求解

    一.最长公共子序列 经典的动态规划问题,大概的陈述如下: 给定两个序列a1,a2,a3,a4,a5,a6......和b1,b2,b3,b4,b5,b6.......,要求这样的序列使得c同时是这两个 ...

  3. 最长递增子序列 O(NlogN)算法

    转自:点击打开链接 最长递增子序列,Longest Increasing Subsequence 下面我们简记为 LIS. 排序+LCS算法 以及 DP算法就忽略了,这两个太容易理解了. 假设存在一个 ...

  4. 51nod 1134 最长递增子序列

    题目链接:51nod 1134 最长递增子序列 #include<cstdio> #include<cstring> #include<algorithm> usi ...

  5. 动态规划 - 最长递增子序列(LIS)

    最长递增子序列是动态规划中经典的问题,详细如下: 在一个已知的序列{a1,a2,...,an}中,取出若干数组组成新的序列{ai1,ai2,...,aim},其中下标i1,i2,...,im保持递增, ...

  6. 最长递增子序列问题 nyoj 17单调递增最长子序列 nyoj 79拦截导弹

    一,    最长递增子序列问题的描述 设L=<a1,a2,…,an>是n个不同的实数的序列,L的递增子序列是这样一个子序列Lin=<aK1,ak2,…,akm>,其中k1< ...

  7. 2.16 最长递增子序列 LIS

    [本文链接] http://www.cnblogs.com/hellogiser/p/dp-of-LIS.html [分析] 思路一:设序列为A,对序列进行排序后得到B,那么A的最长递增子序列LIS就 ...

  8. 【动态规划】拦截导弹_dilworth定理_最长递增子序列

    问题 K: [动态规划]拦截导弹 时间限制: 1 Sec  内存限制: 256 MB提交: 39  解决: 10[提交][状态][讨论版] 题目描述 张琪曼:“老师,修罗场是什么?” 墨老师:“修罗是 ...

  9. COGS731 [网络流24题] 最长递增子序列(最大流)

    给定正整数序列x1,..., xn (n<=500).(1)计算其最长递增子序列的长度s.(2)计算从给定的序列中最多可取出多少个长度为s的递增子序列.(3)如果允许在取出的序列中多次使用x1和 ...

随机推荐

  1. java Serializable和Externalizable序列化反序列化详解--转

    一.什么是序列化? “对象序列化”(Object Serialization)是 Java1.1就开始有的特性. 简单地说,就是可以将一个对象(标志对象的类型)及其状态转换为字节码,保存起来(可以保存 ...

  2. UITableView的编辑(插入、删除、移动)

    先说两个方法beginUpdates和endUpdates,几点注意事项: 一般我们把行.块的插入.删除.移动写在由这两个方法组成的函数块中.如果你不是在这两个函数组成的块中调用插入.删除.移动方法, ...

  3. [转] thrift的使用介绍

    http://gemantic.iteye.com/blog/1199214 一.About  thrift   二.什么是thrift,怎么工作? 三.Thrift  IDL 四.Thrift   ...

  4. Struts2与jQuery.ajax()的结合

    1.客户端是通过$.ajax()方法向login.action传递数据:2.其中action中execute()方法返回值为空,并通过[ServletActionContext.getResponse ...

  5. 获取EnterpriseLibrary企业库配置文件中ConnectionStrings(原创)

    在使用企业类库时想取出单独企业配置文件中的连接字符串遍历,并放到自己的数据库处理类中,在查找了很久的资料后都没有找到,于是自己探索着写了一个,共享给大家以做参考: ConfigurationSourc ...

  6. Starting nagios:This account is currently not available nagios

    nagios在启动时报错 # service nagios restartRunning configuration check…done.Stopping nagios: done.Starting ...

  7. PHP 杂项 函数

    安装 杂项函数是 PHP 核心的组成部分.无需安装即可使用这些函数. Runtime 配置 杂项函数的行为受 php.ini 文件中的设置的影响. 杂项配置选项: 名称 默认 描述 可更改 ignor ...

  8. mysql 数据库字符串替换

    UPDATE `table_name` SET `field_name` = replace (`field_name`,'from_str','to_str') WHERE `field_name` ...

  9. ContentProvider URI的组成

    ContentProvider URI由哪几部分组成 ContentProvider URI与HTTP URI类似,由以下4部分组成: 1.content://   相当于HTTP URI中的http ...

  10. WDCP控制面板安装卸载

    安装 安装源码 WDCP提供两种安装模式,一种是源码安装,一种是RPM包安装,众所周知,源码安装虽然安装时要比RPM包安装繁琐,但是使用上要节省内存.所以我这里主要介绍源码安装. 首先是下载安装源代码 ...