ZOJ 1093 && NYoj16(DP)

~~~~

两个题目大致类似,NYOJ上面那道题就是小白上的矩形嵌套啦。

都是先对长宽进行排序,然后逐层更新最大值(边更新边记录)。

好了,不说了。

题目链接:

http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=1093

http://acm.nyist.net/JudgeOnline/problem.php?pid=16

~~~~

ZOJ1093:

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define N 33
using namespace std;

struct node
{
    int l,w,h;
}s[N*3];
//按长宽大小排序
bool cmp(node a,node b)
{
    if(a.l==b.l)
        return a.w<b.w;
    return a.l<b.l;
}
int main()
{
    int n,T=0;
    while(~scanf("%d",&n),n)
    {
        int cnt=0;
        //对于每个石头,都有三种放置的方法(其实是六种)。
        //这里写的好挫,勿喷。。
        for(int i=0;i<n;i++)
        {
            int a,b,c,ta,tb,tc;
            scanf("%d %d %d",&a,&b,&c);

            ta=a;tb=b;tc=c;
            s[cnt].h=a;
            if(b<c) swap(tb,tc);
            s[cnt].l=tb;
            s[cnt++].w=tc;

            ta=a;tb=b;tc=c;
            s[cnt].h=b;
            if(a<c) swap(ta,tc);
            s[cnt].l=ta;
            s[cnt++].w=tc;

            ta=a;tb=b;tc=c;
            s[cnt].h=c;
            if(a<b) swap(ta,tb);
            s[cnt].l=ta;
            s[cnt++].w=tb;
        }
        sort(s,s+cnt,cmp);
        int ans=0;
        for(int i=0;i<cnt;i++)
        {
            int tm=0;
            for(int j=0;j<i;j++)
            {
                //最小的石头上面可以放置的石头的最大高度。
                //然后一层一层的更新。
                if(s[i].l>s[j].l && s[i].w>s[j].w && s[j].h>tm)
                    tm=s[j].h;
            }
            s[i].h+=tm;
            ans=max(ans,s[i].h);
        }
        printf("Case %d: maximum height = %d\n",++T,ans);
    }
    return 0;
}

~~~~

NYOJ16:

#include<cstdio>
#include<iostream>
#include<algorithm>
#include<cstring>
#define N 1111
using namespace std;

int dp[N];
struct node
{
    int l;
    int w;
}tri[N];

bool cmp(node a,node b)
{
    if(a.l==b.l)
        return a.w>b.w;
    return a.l>b.l;
}
int main()
{
    int t;
    scanf("%d",&t);
    while(t--)
    {
        int n;
        scanf("%d",&n);
        for(int i=0;i<n;i++)
        {
            int u,v;
            scanf("%d%d",&u,&v);
            if(u<v) swap(u,v);
            tri[i].l=u;
            tri[i].w=v;
        }
        sort(tri,tri+n,cmp);
        memset(dp,0,sizeof(dp));
        for(int i=0;i<n;i++)
        {
            dp[i]=1;
            for(int j=0;j<i;j++)
            {
                if(tri[i].l<tri[j].l && tri[i].w<tri[j].w && dp[i]<dp[j]+1)
                    dp[i]=dp[j]+1;
            }
        }
        int ans=dp[0];
        for(int i=1;i<n;i++)
            ans=max(ans,dp[i]);
        printf("%d\n",ans);
    }
    return 0;
}

ZOJ 1093 && NYoj16(DP)

时间: 2024-10-01 07:00:16

ZOJ 1093 && NYoj16(DP)的相关文章

ZOJ 1093

排序DP(相当于最长不下降子序列) 如果把一块砖块的所有6种摆放方式转化为6种不同的砖块: 即相当于有6n种砖块,然后按照一个方向从大到小排序: 再依次检查每一块与其下面的所有砖块是否满足摆放条件: 将每一块砖块放到塔中能够获得的最大高度记录到数组height[N]中: 则该数组中的最大值就是该题的解了: #include <iostream>#include <algorithm>#include "cstdio"using namespace std;#de

zoj 3640 概率dp

http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=4808 Background     If thou doest well, shalt thou not be accepted? and if thou doest not well, sin lieth at the door. And unto thee shall be his desire, and thou shalt rule over him. And Cai

zoj 3299 概率dp

http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3329 回头重推式子 题解:http://blog.csdn.net/morgan_xww/article/details/6775853#reply 学到: 1.目前做的两道期望的状态转移方程都是从大向小推,定义方式:dp[i][j][k]....  满足i,j,k时,要达到upbound(i),upbound(j),upbound(k),需要XX的期望 2.待定系数的方

zoj 3329 概率dp

看了这么多,也就是个递推 1 /* 2 ZOJ 3329 3 题意:有三个骰子,分别有k1,k2,k3个面. 4 每次掷骰子,如果三个面分别为a,b,c则分数置0,否则加上三个骰子的分数之和. 5 当分数大于n时结束.求游戏的期望步数.初始分数为0 6 7 设dp[i]表示达到i分时到达目标状态的期望,pk为投掷k分的概率,p0为回到0的概率 8 则dp[i]=∑(pk*dp[i+k])+dp[0]*p0+1; 9 都和dp[0]有关系,而且dp[0]就是我们所求,为常数 10 设dp[i]=A

ZOJ 3626(树形DP+背包+边cost)

题目链接: http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3626 题目大意:树中取点.每过一条边有一定cost,且最后要回到起点.给定预算m,问最大价值. 解题思路: 首先要注意这题要回到起点,由于树的特殊结构(每个结点只有一个父亲)也就是说,要回到开头, 开销是2倍.所以首先m/=2. 然后就是树形背包的求解,这题的cost在边,所以for写法变成如下: for(m....j....0)     for(0....k

ZOJ 3201 树形dp+背包(简单题)

#include<cstdio> #include<vector> #include<cstring> #include<iostream> using namespace std; const int MAXN = 110; vector<int>a[MAXN]; int n,m,v[MAXN],vis[MAXN],dp[MAXN][MAXN]; void dfs(int root) { dp[root][1] = v[root]; vis[r

5thweek.problem_B(zoj 1093) LIS

Description 一组研究人员正在设计一项实验,以测试猴子的智商.他们将挂香蕉在建筑物的屋顶,同时,提供一些砖块给这些猴子.如果猴子足够聪明,它应当能够通过合理的放置一些砖块建立一个塔,并爬上去吃他们最喜欢的香蕉. 研究人员有n种类型的砖块,每种类型的砖块都有无限个.第i块砖块的长宽高分别用xi,yi,zi来表示. 同时,由于砖块是可以旋转的,每个砖块的3条边可以组成6种不同的长宽高. 在构建塔时,当且仅当A砖块的长和宽都分别小于B砖块的长和宽时,A砖块才能放到B砖块的上面,因为必须留有一

zoj 3822概率dp

Domination Time Limit: 8 Seconds Memory Limit: 131072 KB Special Judge Edward is the headmaster of Marjar University. He is enthusiastic about chess and often plays chess with his friends. What's more, he bought a large decorative chessboard with N r

zoj 3822 概率dp

1 /* 2 题目大意:一个n*m的棋盘,每天放一个棋子,每行每列至少有一个棋子时结束.求达到每行每列至少有一个棋子的天数的数学期望. 3 */ 4 #include <iostream> 5 #include <cstdio> 6 #include <cstring> 7 using namespace std; 8 9 const int maxn=55; 10 double dp[maxn*maxn][maxn][maxn];//放i颗棋子,j行有棋子,k列有棋子