字节跳动青训营|豆包MarsCode AI刷题|补给站最优花费问题

90 阅读2分钟

问题描述

小明想从A徒步到B,总路程需要M天,路程中为了确保安全,小明每天需要消耗1份食物。
在起点及路程当中,零星分布着N个补给站,可以补充食物,不同补给站的食物价格可能不同。
请问小明若要安全完成徒步,最少需要花费多少钱呢?

输入格式

第一行为两个正整数MN,代表总路程M天,补给站个数N
接下来N行,每行有两个非负整数AB代表一个补给站,表示第A天经过该补给站,每份食物的价格为B元。
A是从0开始严格递增的,即起点一定有补给站,补给站是按位置顺序给出的,且同一个位置最多有一个补给站。

输出格式

输出一个整数,表示最少花费的金额

输入样例

5 4  
0 2  
1 3  
2 1  
3 2  

输出样例

7

说明:在第0天买2份食物,在第2天买3份食物,共花费7元

数据范围

  • 30%的数据,N <= M <= 100, 0 <= A < M, 0 <= B <= 1000
  • 80%的数据,N <= M <= 10000, 0 <= A < M, 0 <= B <= 1000
  • 100%的数据,N <= M <= 1000000, 0 <= A < M, 0 <= B <= 1000

分析

  1. 动态规划的简化

    • 我们不需要一个完整的DP数组来存储每一天的最小花费,因为我们只关心到当前天为止的最小花费。
    • 我们可以用一个变量来跟踪到当前天为止的最小花费,并在遇到新的补给站时更新这个变量。
  2. 贪心策略

    • 在每一天,小明都需要确保有食物供应。如果当前天有补给站,则比较当前补给站的价格与之前记录的最小价格,选择价格较低的那个购买食物。
    • 如果没有当前天的补给站,则默认使用之前记录的最小价格购买食物。
  3. 实现

    • 遍历每一天,同时遍历补给站数组,更新到当前天为止的最小食物价格。
    • 累加每一天的最小花费,得到总花费。

代码

public class Main {
    public static int solution(int m, int n, int[][] p) {
        // Edit your code here
        int minprice=Integer.MAX_VALUE;
        int sum=0;
        for(int i=0;i<m;i++){
            for(int j=0;j<n;j++){
                if(p[j][0]==i){
                    minprice=Math.min(minprice,p[j][1]);
                    break;
                }
            }
            sum+=minprice;
        }
        return sum;

    }

    public static void main(String[] args) {
        // Add your test cases here

        System.out.println(solution(5, 4, new int[][]{{0, 2}, {1, 3}, {2, 1}, {3, 2}}) == 7);
    }
}