zoukankan      html  css  js  c++  java
  • Codeforces Round #677 (Div. 3)

    Codeforces Round #677 (Div. 3)

    F. Zero Remainder Sum

    直接dfs枚举所有情况, 然后在加个记忆化

    #include<bits/stdc++.h>
    using namespace std;
    
    typedef long long ll;
    
    int dp[80][80][70][80];
    
    int mp[100][100], k, n, m;
    
    bool judge(int x, int y) {
        if (x < 1 || y < 1 || x > n || y > m) {
            return false;
        }
        return true;
    }
    
    int dfs(int x, int y, int cnt, int sum) {
        if (!judge(x, y)) {
            if (sum == 0) {
                return 0;
            }
            return -1e8;
        }
        if (dp[x][y][cnt][sum] != -1) return dp[x][y][cnt][sum];
    
        int ans = -1e8;
        ans = max(ans, dfs(x, y + 1, cnt, sum));
        ans = max(ans, dfs(x + 1, 1, 0, sum));
        if (cnt < m / 2) {
            ans = max(ans, dfs(x, y + 1, cnt + 1, (sum + mp[x][y]) % k ) + mp[x][y]);
        }
        if (cnt < m / 2) {
            ans = max(ans, dfs(x + 1, 1, 0, (sum + mp[x][y]) % k ) + mp[x][y]);
        }
        return dp[x][y][cnt][sum] = ans;
    }
    
    
    
    int main() {
        cin >> n >> m >> k;
        for (int i = 1; i <= n; i++) {
            for (int j = 1; j <= m; j++) {
                cin >> mp[i][j];
            }
        }
        memset(dp, -1, sizeof(dp));
        cout << dfs(1, 1, 0, 0) << endl;
    }
    

    G. Reducing Delivery Cost

    先用迪杰斯特拉跑多源最短路, 求出(dist[i][j]) i 到j的最短距离, 然后枚举删的边(u, v) 假设当前要算的是 s到t的最短路, 删掉u,v时 那么最短路有可能变成,(dist[s][u] + dist[v][t])或者 (dist[s][v] + dist[u][t])或者是(dist[s][t])取最小就行了

    代码:

    #include<bits/stdc++.h>
    using namespace std;
    typedef long long ll;
    const int N = 1e3 + 7;
    
    int dist[N][N], n, m, k, vis[N] ;
    
    vector<pair<int, int> > g[N];
    
    struct node {
        int d, v;
        bool operator <(const node x) const{
            return d > x.d;
        }
    };
    
    priority_queue<node>q;
    
    void dj (int s) {
        for (int i = 1; i <= n; i++) {
            dist[s][i] = 1e8;
            vis[i] = 0;
        }
        dist[s][s] = 0;
        q.push({0, s});
        while (q.size()) {
            node cd = q.top();
            q.pop();
            if (vis[cd.v]) continue;
            vis[cd.v] = 1;
            for (auto it: g[cd.v]) {
                int to = it.first;
                int cost = it.second;
                if (dist[s][to] > dist[s][cd.v] + cost) {
                    dist[s][to] = dist[s][cd.v] + cost;
                    q.push({dist[s][to], to});
                }
            }
        }
    }
    
    vector<pair<int, int> >cnt;
    
    struct edge{
        int u, v, w;
    };
    vector<edge>e;
    
    int main() {
        cin >> n >> m >> k;
        for (int i = 1; i <= m; i++) {
            int u, v, w;
            cin >> u >> v >> w;
            g[u].push_back({v, w});
            g[v].push_back({u, w});
            e.push_back({u, v, w});
        }
        for (int i = 1; i <= k; i++) {
            int u, v;
            cin >> u >> v;
            cnt.push_back({u, v});
        }
    
        for (int i = 1; i <= n; i++) {
            dj(i);
        }
        long long ans = 0;
        for (int i = 0; i < cnt.size(); i++) {
            ans += 1ll* dist[cnt[i].first][cnt[i].second];
        }
        long long minn = INT_MAX;
        for (int i = 0; i < e.size(); i++) {
            ll cat = ans;
            int u = e[i].u, v = e[i].v, w = e[i].w;
            for (int j = 0; j < cnt.size(); j++) {
                ll res = dist[cnt[j].first][u] + dist[cnt[j].second][v];
                ll cn = 0;
              
                if (res < dist[cnt[j].first][cnt[j].second]) {
                    cn = dist[cnt[j].first][cnt[j].second] - res;
                }
                res = dist[cnt[j].first][v] + dist[cnt[j].second][u];
                if (res < dist[cnt[j].first][cnt[j].second]) {
                    cn = max(cn, dist[cnt[j].first][cnt[j].second] - res);
                }
                cat = cat - cn;
            }
        
            minn = min(minn, cat);
        }
        cout << minn << endl;
    
    }
    
  • 相关阅读:
    计算任意两个日期的间隔天数
    题目标题: 排它平方数
    历届试题 剪格子
    历届试题 翻硬币
    C语言中%d,%o,%f,%e,%x的意义
    历届试题 买不到的数目
    九度 OJ1008 hdu 3790
    南洋理工 OJ 115 城市平乱 dijstra算法
    蓝桥杯 错误票据 原创代码+思路
    历届试题 连号区间数
  • 原文地址:https://www.cnblogs.com/BOZHAO/p/13850895.html
Copyright © 2011-2022 走看看