zoukankan      html  css  js  c++  java
  • 内容敏感图像压缩

    内容敏感图像压缩

    Background

    在清华大学存活,你需要有极强的文献阅读能力……【该背景与本题无关】

    Description

    有一张N*M的方格纸,每一个格子上写了一个正整数,现在我们把方格纸首尾相连,组成一个高度为N,周长为M的圆柱体的侧表面。

    现在你需要找到一个从上到下贯穿该圆柱侧表面的长度为N的路径,使得路径上的权值尽量小。其中,路径上相邻的两点必须是“八连通的”。

    Input  Format

    第一行两个整数N,M。接下来若干行是一个N* M的矩阵

    Output  Format

    一行一个整数,表示答案。

    Sample  Input

    3  3

    1    2  2

    2    2  1

    3    2  1

    Sample  Output

    3

    Constraint

    ·对于20%数据,min(N,M) = 1

    ·对于40%数据N,M <= 40

    ·对于约50%数据,路径不经过圆柱体侧表面。

    ·对于100%数据,N,M <= 3000

    所以,这道题的名字有什么意义呢?可以考完试看一看题目后面附的文章。

    错误代码0分

    #include<cstdio>

    #include<cmath>

    #include<algorithm>

    #include<cstring>

    using namespace std;

    int n,i,j,k,m,a[3005][3005] = {30005},p,ans;

    int main()

    {

             freopen("compress.in","r",stdin);

             freopen("compress.out","w",stdout);

             scanf("%d %d",&n,&m);

             for(i = 1;i <= n;i++)

             {

                       for(j = 1;j <= m;j++)

                       {

                                scanf("%d",&a[i][j]);

                       }

             }

             if(m != 1)

             {

                       for(i = n - 1;i >= 1;i--)

                       {

                                for(j = m;j >= 1;j--)

                                {

                                         if(j == 1)

                                         {

                                                   p = min(a[i + 1][m] + a[i][j],a[i + 1][j] + a[i][j]);

                                                   a[i][j] = min(a[i + 1][j + 1] + a[i][j],p);

                                         }

                                         else if(j == m)

                                         {

                                                   p = min(a[i + 1][1] + a[i][j],a[i + 1][j] + a[i][j]);

                                                   a[i][j] = min(a[i + 1][j - 1] + a[i][j],p);

                                         }

                                         else

                                         {

                                                   p = min(a[i + 1][j - 1] + a[i][j],a[i + 1][j] + a[i][j]);

                                                   a[i][j] = min(a[i + 1][j + 1] + a[i][j],p);

                                         }

                                }

                       }

                       ans = a[1][1];

                       for(i = 2;i <= m;i++)

                       {       

                                ans = min(a[1][i],ans);

                       }

             }

             else

             {

                       ans = 0;

                       for(i = 1;i <= n;i++)

                       {

                                ans = ans + a[i][1];

                       }

             }

             printf("%d",ans);

             return 0;

    }

    正确答案:

    #include<iostream>

    #include<cstdio>

    #include<cstring>

    #include<algorithm>

    using namespace std;

    #define MAXN 3010

    #define INF 0x3f3f3f3f

    int dp[MAXN][MAXN*2];

    int mat[MAXN][MAXN*2];

    int nextInt() {

             int ans=0;

             char c = 0;

             while (c=getchar(),c<'0'||c>'9');

             while (ans = ans*10+c-'0',c=getchar(),c>='0' && c<='9');

             return ans;

    }//快速读入

    int main() {

    //      freopen("compress.in","r",stdin);

    //      freopen("compress.out","w",stdout);

             int n,m;

             scanf("%d%d",&n,&m);

             memset(mat,0x3f,sizeof(mat));//把每一个点都变成最大值

             memset(dp,0x3f,sizeof(dp)); //把每个路径都变成最大值

             for (int i=1;i<=n;i++)

                       for (int j=1;j<=m;j++)

                       {

                                int x;

                                x = nextInt();

                                //scanf("%d",&x);

                                mat[i][j] = mat[i][j+m] = x;//分环成列在复制一个放在右面

                       }

             for (int j=1;j<=m;j++)

                       dp[0][j] = 0;//假设最上面有一层为0的

             for (int i=1;i<=n;i++)

                       for (int j=1;j<=m*2;j++)

                                dp[i][j] = min(dp[i-1][j-1],min(dp[i-1][j],dp[i-1][j+1])) + mat[i][j];//枚举每一个点他只有三种可能来的方向取最小值

             int ans = INF;

             for (int j=1;j<=m*2;j++)

                       ans = min(ans,dp[n][j]);//把最后一行所有的尽可能的最小值再比较得出最最小的值

             printf("%d ",ans);//输出答案

             return 0;

    }

    ****其实这道题我应该只是错在了没有化环为列。

    内容敏感图像压缩

    给你一个矩阵让你找到一个路径dp方程组写对了

    常数优化,开o2

    这道题如果说是一个环的话怎么办

    就是今天上午讲的化环为列

    完完整整复制一遍在棋盘上跑就行

    就是一个过两边的复制问题

  • 相关阅读:
    SpringCloud学习第四篇:Feign学习(Hoxton.SR4)
    SpringCloud学习第三篇:Ribbon负载均衡(Hoxton.SR4)
    SpringCloud学习第二篇:使用Consul注册中心(Greenwich-SR1版本)
    SpringCloud学习第一篇:服务的注册与发现Eureka(Hoxton.SR4)
    SpringBoot+Mycat+APO实现读写分离
    SpringBoot+activeMq
    自动化测试适用场景和难点
    软件测试理论
    软件测试理论中的注意事项
    python自动化:monkey测试的云测
  • 原文地址:https://www.cnblogs.com/rax-/p/9314749.html
Copyright © 2011-2022 走看看