LeetCode-312. Burst Balloons [C++][Java]

本文介绍了如何解决LeetCode上的第312题——爆破气球以获取最大数量的硬币。解题策略包括分治递归和动态规划,通过C++和Java两种编程语言实现。通过爆破不同位置的气球,计算每次爆破能得到的硬币,并选择最优策略。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

LeetCode-312. Burst Balloonshttps://leetcode.com/problems/burst-balloons/

题目描述

You are given n balloons, indexed from 0 to n - 1. Each balloon is painted with a number on it represented by an array nums. You are asked to burst all the balloons.

If you burst the ith balloon, you will get nums[i - 1] * nums[i] * nums[i + 1] coins. If i - 1 or i + 1 goes out of bounds of the array, then treat it as if there is a balloon with a 1 painted on it.

Return the maximum coins you can collect by bursting the balloons wisely.

Example 1:

Input: nums = [3,1,5,8]
Output: 167
Explanation:
nums = [3,1,5,8] --> [3,5,8] --> [3,8] --> [8] --> []
coins =  3*1*5    +   3*5*8   +  1*3*8  + 1*8*1 = 167

Example 2:

Input: nums = [1,5]
Output: 10

Constraints:

  • n == nums.length
  • 1 <= n <= 300
  • 0 <= nums[i] <= 100

解题思路

【C++】

1. 分治递归

class Solution {
public:
    vector<vector<int>> dp;
    int solve(int i,int j,vector<int>& nums){
        if (i + 1 == j) {return 0;}
        if (dp[i][j] != -1) {return dp[i][j];}
        int ans = 0;
        for (int k = i + 1; k < j; k++){
            if (dp[i][k] == -1) {dp[i][k] = solve(i, k, nums);}
            if (dp[k+1][j] == -1) {dp[k][j] = solve(k, j, nums);}
            ans = max(ans, dp[i][k] + dp[k][j] + nums[i] * nums[k] * nums[j]);
        }
        return dp[i][j] = ans;
    }

    int maxCoins(vector<int>& nums) {
        nums.insert(nums.begin(), 1);
        nums.push_back(1);
        int n = nums.size();
        dp = vector<vector<int>>(n, vector<int>(n, -1));
        return solve(0, n-1, nums);
    }
};

2. 动态规划

class Solution {
public:
    int maxCoins(vector<int>& nums) {
       int n = nums.size();
       vector<vector<int>> dp(n, vector<int>(n));
       for(int g = 0; g < n; g++){
           for(int i = 0, j = g; j<n; i++, j++){
               int maxval = -1;
               for (int k = i; k <= j; k++){
                   int left = k == i ? 0 : dp[i][k-1];
                   int right = k == j ? 0 : dp[k+1][j];
                   int brust =(i == 0 ? 1 : nums[i-1])*nums[k]*(j == n-1 ? 1 : nums[j+1]);
                   int total = left+ right + brust;
                   maxval = max(maxval, total);
               }
               dp[i][j] = maxval;
           }
       }
       return dp[0][n-1];
    }
};

【Java】

class Solution {
    public int maxCoins(int[] nums) {
        int n = nums.length;
        if (n==0) return 0;
        if (n==1) return nums[0];
        int[][] memo = new int[n][n];
        for (int len=1; len<=n; len++) {
            for (int st=0,end=st+len-1; end<n; st++,end++) {
                for (int k=st; k<=end; k++) {
                    int cost= ((k==st) ? 0 : memo[st][k-1])+ ((k==end) ? 0 : memo[k+1][end]);
                    cost += ((st==0) ? 1 : nums[st-1])*nums[k]*((end==n-1 ) ? 1 : nums[end+1]); 
                    memo[st][end] = Math.max(memo[st][end], cost);
                }
            }
        }
        return memo[0][n-1];
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

贫道绝缘子

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值