string的用法
https://www.cnblogs.com/xFreedom/archive/2011/05/16/2048037.html
vector
https://www.cnblogs.com/mengfanrong/p/3770971.html
类型转换
https://blog.csdn.net/xiaoquantouer/article/details/51746476
导弹拦截
#include <iostream>
#include<bits/stdc++.h>
#define MAX 100100
int f[MAX];//f[i]表示以i结尾的最长非升子序列的长度
int h[MAX];
int n;
int b[MAX];//b[n]长度为n的非升子序列的结尾值,即最大值
using namespace std;
void init()
{
memset(f,0,sizeof(f));
memset(b,0,sizeof(b));
for(int i = 0;i < n;i++) f[i] = 1;
}
int lbs1()//最长非升子序列
{
int ans = 0;
for(int i = 1;i < n;i++)//求 f[i]
{
int ma = 1;
for(int j = 0;j < i;j++)
{
if(h[i] <= h[j])
ma = max(ma,f[j]+1);
}
f[i] = ma;
ans = max(ans,ma);
}
return ans;
}
int bina2(int k,int num)//二分法,b上升序列,返回大于或等于num的最小值的下标
//若只是返回大于num的最小值的下标 那么当b数组为2 4 8 9 14 而num为8时,将返回9的下标,并将9改为8
//b数组就成了2 4 8 8 14,而此问题是最长升序,而非最长非递减
{
if(num < b[1])
return 1;
int low = 1,high = k;
int mid;
// while(low < high)
// {
// mid = (low+high)/2;
// if(b[mid] >= num)
// high = mid;
// else
// low = mid+1;
// }
// return low;
for(;low < high-1;)
{
mid = (low+high)/2;
if(b[mid]<num)//将<= 改为 <,
{
low = mid;
}
else
{
high = mid;
}
}
return high;
}
int lbs4()
{
int k = 1;
b[1] = h[0];
for(int i = 1;i < n;i++)
{
if(h[i] > b[k])
{
b[++k] = h[i];
}
else
{
b[bina2(k,h[i])] = h[i];
}
}
return k;
}
int lbs3()//最长上升子序列
{
int ans = 0;
for(int i = 1;i < n;i++)//求 f[i]
{
int ma = 1;
for(int j = 0;j < i;j++)
{
if(h[i] > h[j])
ma = max(ma,f[j]+1);
}
f[i] = ma;
ans = max(ans,ma);
}
return ans;
}
int binary(int b[],int k,int num)//二分法,b非升序列,返回小于num的最大值的下标
{
if(num > b[1])
return 1;
int mid = 0;
int low = 1,high = k;
for(;low < high-1;)
{
mid = (low+high)/2;
if(b[mid]>=num)
{
low = mid;
}
else
{
high = mid;
}
}
return high;
}
int lbs2()
{
int k=1;
b[1] = h[0];
for(int i = 1;i < n;i++)
{
if(h[i] <= b[k])
{
b[++k] = h[i];
}
else
{
b[binary(b,k,h[i])] = h[i];
}
}
return k;
}
int main()
{
// cin >> n;
// for(int i = 0;i < n;i++)
// {
// cin >> h[i];
// }
n = 0;
while(scanf("%d",&h[n++])!=EOF);
n--;
init();
int ans1,ans2;
ans1 = lbs2();
init();
ans2 = lbs4();
cout << ans1 << endl << ans2 << endl;
}
嵌套矩形
#include<bits/stdc++.h>
#define MAX 300
typedef struct{
int length;
int width;
}rectangle;
rectangle rec[MAX];
int G[MAX][MAX] = {0};//G[i][j] 表示j结点到i结点有一个有向边,rec[i]可包含rec[j]
int f[MAX] = {0};//f[i]以i为结尾的最长路径,即rec[i]最多能装多少个矩形
using namespace std;
int n;
void createGraph()
{
for(int i = 0;i < n;i++)
for(int j = 0;j < n;j++)
{
if(rec[i].length > rec[j].length && rec[i].width > rec[j].width)
{
G[i][j] = 1;
}
else
G[i][j] = 0;
}
}
int dp(int i)
{
if(f[i]!=0) return f[i];
else f[i]=1;
for(int j = 0;j < n;j++)
{
if(G[i][j]==1)
{
int tmp = dp(j);
f[i]=max(f[i],tmp+1);
}
}
return f[i];
}
int main()
{
int a,b,ans = 0;
cin >> n;
for(int i = 0;i < n;i++)
{
cin >> a >> b;
rec[i].length = a>b ? a:b; //长大于宽
rec[i].width = a<b?a:b;
}
createGraph();
for(int i = 0;i <n;i++)
f[i]=0;
for(int i = 0;i < n;i++)
{
int tmp = dp(i);
ans = ans>tmp?ans:tmp;
}
cout << ans <<endl;
}