zoukankan      html  css  js  c++  java
  • bzoj3628: [JLOI2014]天天酷跑

    题目链接

    bzoj3628: [JLOI2014]天天酷跑

    题解

    开始读错题目了,尴尬
    由于题目说的跳跃次数和高度是在一开始设定的。
    发现枚举一下记忆化搜索就可以过了
    要注意,跳到最高点是可以不下坠继续连跳的
    另外,上边界不能到达

    代码

    #include<cstdio> 
    #include<cstring> 
    #include<algorithm> 
    inline int read() { 
        int x = 0,f = 1; 
        char c = getchar(); 
        while(c < '0' || c > '9'){if(c == '-') f = -1; c = getchar(); } 
        while(c <= '9' && c >= '0') x = x * 10 + c - '0',c = getchar(); 
        return x * f; 
    } 
    const int maxn = 100007; 
    int n,m,c1,c2,h,freq; 
    #define INF 100000007
    int a[23][maxn]; 
    int f[23][maxn][6]; 
    bool vis[23][maxn][6]; 
    int dfs(int x,int y,int jumpcnt) { 
        if(y > n) return 0; 
        if(a[x][y] == -1) return  -INF; 
        if(vis[x][y][jumpcnt]) return f[x][y][jumpcnt]; 
        if(x == 1)jumpcnt = 0; 
        int tmp = -INF ;  
        if(jumpcnt < freq) { 
            int Sum = 0,tx = x,ty = y; bool can = true; 
            for(int i = 1;i < h;i ++) { 
                tx ++,ty ++; 
                if(a[tx][ty] == -1) {can = false; break; } Sum += a[tx][ty];
            } 
            if(can) tmp = std::max(tmp,Sum + dfs(tx + 1,ty + 1,jumpcnt + 1)); 
        } 
        if(x == 1) tmp = std::max(tmp, dfs(x,y + 1,0)) ; 
        if(x > 1) tmp = std::max(tmp, dfs(x - 1,y + 1,jumpcnt)); 
        f[x][y][jumpcnt] = tmp + a[x][y]; 
        vis[x][y][jumpcnt] = true;  
        return f[x][y][jumpcnt];  
    } 
    int ans = -INF ,an1,an2; 
    int main() { 
        n = read(),m = read(), c1 = read(),c2 = read(); 
        for(int i = 1;i <= m;++ i) for(int j = 1;j <= n;++ j) 
            a[i][j] = read(); 
        for(freq = 1;freq <= 5;++ freq) 
            for(h = 1;h * freq < m;++ h) { 
                memset(vis,0,sizeof vis); 
                memset(f,0,sizeof f); 
                int sum = dfs(1,0,m) - (h - 1) * c1 - (freq - 1) * c2; 
                if(sum > ans) ans = sum , an1 = h, an2 = freq; 
            } 
        if(ans > 0) printf("%d %d %d
    ",ans,an2,an1); 
        else puts("mission failed"); 
        return 0 ; 
    }  #include<cstdio> 
    #include<cstring> 
    #include<algorithm> 
    inline int read() { 
        int x = 0,f = 1; 
        char c = getchar(); 
        while(c < '0' || c > '9'){if(c == '-') f = -1; c = getchar(); } 
        while(c <= '9' && c >= '0') x = x * 10 + c - '0',c = getchar(); 
        return x * f; 
    } 
    const int maxn = 100007; 
    int n,m,c1,c2,h,freq; 
    #define INF 100000007
    int a[23][maxn]; 
    int f[23][maxn][6]; 
    bool vis[23][maxn][6]; 
    int dfs(int x,int y,int jumpcnt) { 
        if(y > n) return 0; 
        if(a[x][y] == -1) return  -INF; 
        if(vis[x][y][jumpcnt]) return f[x][y][jumpcnt]; 
        if(x == 1)jumpcnt = 0; 
        int tmp = -INF ;  
        if(jumpcnt < freq) { 
            int Sum = 0,tx = x,ty = y; bool can = true; 
            for(int i = 1;i < h;i ++) { 
                tx ++,ty ++; 
                if(a[tx][ty] == -1) {can = false; break; } Sum += a[tx][ty];
            } 
            if(can) tmp = std::max(tmp,Sum + dfs(tx + 1,ty + 1,jumpcnt + 1)); 
        } 
        if(x == 1) tmp = std::max(tmp, dfs(x,y + 1,0)) ; 
        if(x > 1) tmp = std::max(tmp, dfs(x - 1,y + 1,jumpcnt)); 
        f[x][y][jumpcnt] = tmp + a[x][y]; 
        vis[x][y][jumpcnt] = true;  
        return f[x][y][jumpcnt];  
    } 
    int ans = -INF ,an1,an2; 
    int main() { 
        n = read(),m = read(), c1 = read(),c2 = read(); 
        for(int i = 1;i <= m;++ i) for(int j = 1;j <= n;++ j) 
            a[i][j] = read(); 
        for(freq = 1;freq <= 5;++ freq) 
            for(h = 1;h * freq < m;++ h) { 
                memset(vis,0,sizeof vis); 
                memset(f,0,sizeof f); 
                int sum = dfs(1,0,m) - (h - 1) * c1 - (freq - 1) * c2; 
                if(sum > ans) ans = sum , an1 = h, an2 = freq; 
            } 
        if(ans > 0) printf("%d %d %d
    ",ans,an2,an1); 
        else puts("mission failed"); 
        return 0 ; 
    }  
    
  • 相关阅读:
    hdu 2647 Reward
    hdu 2094 产生冠军
    hdu 3342 Legal or Not
    hdu 1285 确定比赛名次
    hdu 3006 The Number of set
    hdu 1429 胜利大逃亡(续)
    UVA 146 ID Codes
    UVA 131 The Psychic Poker Player
    洛谷 P2491消防 解题报告
    洛谷 P2587 [ZJOI2008]泡泡堂 解题报告
  • 原文地址:https://www.cnblogs.com/sssy/p/9445733.html
Copyright © 2011-2022 走看看