社区讨论

0分求调

P2317[HNOI2005] 星际贸易参与者 2已保存回复 4

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
4 条
当前快照
1 份
快照标识符
@mhjdj61n
此快照首次捕获于
2025/11/04 00:48
4 个月前
此快照最后确认于
2025/11/04 00:48
4 个月前
查看原帖
CPP
#include <bits/stdc++.h>
using namespace std;

struct Planet {
    int A, B, L, P, F;
};

int distance(const vector<Planet>& planets, int i, int j) {
    if (i == -1) return planets[j].L; 
    return planets[j].L - planets[i].L;
}

int main() {
    ifstream fin("input.txt");
    ofstream fout("output.txt");
    int N, M, R, L0;
    fin >> N >> M >> R >> L0;
    
    vector<Planet> planets(N);
    for (int i = 0; i < N; i++) {
        fin >> planets[i].A >> planets[i].B >> planets[i].L >> planets[i].P >> planets[i].F;
    }
    vector<vector<vector<tuple<int, int, int>>>> dp(N, 
        vector<vector<tuple<int, int, int>>>(M + 1, 
        vector<tuple<int, int, int>>(L0 + 1, {-1, -1, 0})));
    for (int i = 0; i < N; i++) {
        int dist = distance(planets, -1, i);
        if (dist > L0) continue;
        
        int fuel_needed = 2; 
        if (fuel_needed > R) continue; 
        
        int remaining_fuel = R - fuel_needed;
        int maintenance_cost = planets[i].F;
        dp[i][M][dist] = {0, -maintenance_cost, remaining_fuel};
        
        if (M >= planets[i].A) {
            int new_w = M - planets[i].A;
            int revenue = planets[i].B;
            int profit = revenue - maintenance_cost;
            dp[i][new_w][dist] = {revenue, profit, remaining_fuel};
        }
    }
    
    for (int i = 0; i < N; i++) {
        for (int w = 0; w <= M; w++) {
            for (int d = 0; d <= L0; d++) {
                if (get<0>(dp[i][w][d]) == -1) continue;
                
                int current_revenue = get<0>(dp[i][w][d]);
                int current_profit = get<1>(dp[i][w][d]);
                int current_fuel = get<2>(dp[i][w][d]);
                
                int buy = 0;
                int fuel_cost = 0;
                
                if (planets[i].P > 0) {

                    int next_cheaper = -1;
                    for (int j = i + 1; j < N; j++) {
                        if (planets[j].P > 0 && planets[j].P < planets[i].P) {
                            next_cheaper = j;
                            break;
                        }
                    }
                    
                    int needed_fuel;
                    if (next_cheaper != -1) {
                        needed_fuel = 2 * (next_cheaper - i); 
                    } else {
                        needed_fuel = 2 * (N - 1 - i); 
                    }

                    if (current_fuel < needed_fuel) {
                        buy = needed_fuel - current_fuel;
                        if (current_fuel + buy > R) {
                            buy = R - current_fuel; 
                        }
                        fuel_cost = buy * planets[i].P;
                    }
                }
                
                int new_fuel = current_fuel + buy;
                int new_profit = current_profit - fuel_cost;

                for (int j = i + 1; j < N; j++) {
                    int dist = distance(planets, i, j);
                    if (d + dist > L0) continue; 
                    
                    int fuel_needed = 2;
                    if (new_fuel < fuel_needed) continue;
                    
                    int remaining_fuel_after = new_fuel - fuel_needed;
                    int new_d = d + dist;
                    int maintenance_cost = planets[j].F;

                    int new_revenue = current_revenue;
                    int j_profit = new_profit - maintenance_cost;
                    
                    if (new_revenue > get<0>(dp[j][w][new_d]) || 
                        (new_revenue == get<0>(dp[j][w][new_d]) && j_profit > get<1>(dp[j][w][new_d]))) {
                        dp[j][w][new_d] = {new_revenue, j_profit, remaining_fuel_after};
                    }

                    if (w >= planets[j].A) {
                        int new_w = w - planets[j].A;
                        new_revenue = current_revenue + planets[j].B;
                        j_profit = new_profit + planets[j].B - maintenance_cost;
                        
                        if (new_revenue > get<0>(dp[j][new_w][new_d]) || 
                            (new_revenue == get<0>(dp[j][new_w][new_d]) && j_profit > get<1>(dp[j][new_w][new_d]))) {
                            dp[j][new_w][new_d] = {new_revenue, j_profit, remaining_fuel_after};
                        }
                    }
                }
            }
        }
    }

    tuple<int, int, int> best = {-1, -1, 0};
    for (int w = 0; w <= M; w++) {
        for (int d = 0; d <= L0; d++) {
            if (get<0>(dp[N-1][w][d]) > get<0>(best) || 
                (get<0>(dp[N-1][w][d]) == get<0>(best) && get<1>(dp[N-1][w][d]) > get<1>(best))) {
                best = dp[N-1][w][d];
            }
        }
    }
    
    if (get<0>(best) == -1) {
        fout << "Poor Coke!" << endl;
    } else {
        fout << get<0>(best) << " " << get<1>(best) << endl;
    }
    
    fin.close();
    fout.close();
    return 0;
}

回复

4 条回复,欢迎继续交流。

正在加载回复...