力扣 279.完全平方数

题目:

给你一个整数 n ,返回 和为 n 的完全平方数的最少数量 。

完全平方数 是一个整数,其值等于另一个整数的平方;换句话说,其值等于一个整数自乘的积。例如,149 和 16 都是完全平方数,而 3 和 11 不是。

示例 1:

输入:n = 12
输出:3 
解释:12 = 4 + 4 + 4

示例 2:

输入:n = 13
输出:2
解释:13 = 4 + 9

提示:

  • 1 <= n <= 104

分析:

和零钱兑换一样,是典型的背包问题,但是和零钱兑换不同的点在于,物品价值项的数量和背包大小有关。所以需要先找出1-n之间的平方数,用数组来存储,数组下标表示值,数组元素由0或1构成。接着从1开始,一直到n,找出构成每个数值的最小平方数数量。每个数值的所需要的最小平方数数量(当前状态),取决于选择的平方数及前一个状态,由此可得状态方程:dp[j]=min(dp[j],dp[j-k]+1)

代码:

class Solution {
public:
    int numSquares(int n) {
        vectorvec(n+1,0);
        //先将平方数存储起来
        for (int i = 1; i <= n; ++i)
        {
            int is = sqrt(i);
            int cmp = ceil(sqrt(i));
            if (is % cmp == 0)//是完全平方数
            {
                vec[i] = 1;
            }
        }
        vectordp(n + 1, n+1);
        dp[0] = 0;
        dp[1] = 1;
        //可以采用零钱兑换的解决思路
        for (int j = 1; j <= n; ++j)
        {
            for (int k = 1; k <= j; ++k)
            {
                //判断k是不是完全平方数
                if (vec[k] == 1)
                {
                    dp[j] = min(dp[j], dp[j - k] + 1);
                }
            }
        }
        if (dp[n] > n)
        {
            return -1;
        }
       
            return dp[n];
    }
};

你可能感兴趣的:(leetcode,算法,数据结构)