zoukankan      html  css  js  c++  java
  • P1052 过河

      一道很好的题,我给的标签:dp,数论,还要用到路径压缩。

      一开始我的想法是剪枝的搜索,但是当我看到数据范围的时候,就彻底放弃了这个想法……109啊……(吓人)

      那怎么办啊……

      路径压缩啊~

      对于为什么能路径压缩,在此简单解释一下:(感谢洛谷题解的提示)

      假设每次走p或者p+1步.我们知道gcd(p,p+1)gcd(p,p+1)=1.

      由扩展欧几里得可知,对于二元一次方程组:

      px+(p+1)y=gcd(p,p+1)是有整数解的,即可得:px+(p+1)y=s是一定有整数解的。

      设px+(p+1)y=s的解为:x=x0+(p+1)t,y=y0-pt。令0<=x<=p(通过增减t个p+1来实现),s>p*(p+1)-1,

      则有:y=(s-px) / (p+1)>=(s-p^2) / (p+1)>(p*(p+1)-1-px) / (p+1)>=0,y=p+1,spx>=p+1,sp2>p+1,p(p+1)1px>=0

      即表示,当 s>=p*(p+1)时,px+(p+1)y=s, 有两个非负整数解,每次走p步或者 p+1 步,p*(p+1) 之后的地方均能够到达。

      如果两个石子之间的距离大于 p*(p+1) ,那么就可以直接将他们之间的距离更改为 p*(p+1) 。

      差不多了。

      综上,得到压缩路径的方法:若两个石子之间的距离> t*(t-1),则将他们的距离更改为 t*(t-1) 。

      因为 t<=10t<=10 ,因此我们可以直接将大于10*9的距离直接化为90。

      但是要注意,对于 s=t 这种特殊情况,这种方法是不成立的应为在这种情况下,每次是不能够走p+1步的,因此需要另外特殊判断。

      下面是代码:

    #include<cstdio>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    #define maxn 20005
    #define INF 99999999
    int dp[maxn],far[maxn],a[maxn],st[maxn];
    int dis,s,t,n;
    int main()
    {
        scanf("%d%d%d%d",&dis,&s,&t,&n);
        int total=0;
        if(s==t)
        {
            int fir;
            for(int i=1;i<=n;i++)
            {
                scanf("%d",&fir);
                total+=((fir%s)==0);
            }
            printf("%d",total);
            return 0;
        }
        for(int i=1;i<=n;i++)
            scanf("%d",&a[i]);//a[i]->第i个石头的位置
         sort(a+1,a+n+1); 
         a[0]=0,far[n+1]=min(dis-a[n],90);
         dis=0;
         for(int i=1;i<=n;i++)
         {
             far[i]=min(a[i]-a[i-1],90);
             dis+=far[i];
             st[dis]=1;
         }
        dis+=far[n+1];
        dp[0]=0;
        for(int i=1;i<=dis+9;i++)
        {
            dp[i]=INF-1;
            for(int j=s;j<=t;j++)
            if(i>=j) dp[i]=min(dp[i],dp[i-j]+st[i]);
        }
        int minn=INF;
        for(int i=dis;i<=dis+9;i++)
        minn=min(minn,dp[i]);
        printf("%d",minn);
        return 0; 
    }

      我发现:fir不写&的话也能得80分呢……

  • 相关阅读:
    springboot中MongoDB的使用
    SpringBoot中发送邮件服务
    springboot中使用RabbitMq
    PostgreSQL学习之【用户权限管理】说明
    Leet Code 19.删除链表的倒数第N个节点
    Kafka集群搭建
    Leet Code 18.四数之和
    Hadoop集群运行情况
    完全分布式Hadoop集群搭建
    Leet Code 17.电话号码的字母组合
  • 原文地址:https://www.cnblogs.com/popo-black-cat/p/10111421.html
Copyright © 2011-2022 走看看