【记忆化搜索】【剪枝】【C++算法】1553吃掉 N 个橘子的最少天数

简介: 【记忆化搜索】【剪枝】【C++算法】1553吃掉 N 个橘子的最少天数

作者推荐

【数位dp】【动态规划】【状态压缩】【推荐】1012. 至少有 1 位重复的数字

涉及知识点

记忆化搜索 剪枝 分类讨论

LeetCode1553. 吃掉 N 个橘子的最少天数

厨房里总共有 n 个橘子,你决定每一天选择如下方式之一吃这些橘子:

吃掉一个橘子。

如果剩余橘子数 n 能被 2 整除,那么你可以吃掉 n/2 个橘子。

如果剩余橘子数 n 能被 3 整除,那么你可以吃掉 2*(n/3) 个橘子。

每天你只能从以上 3 种方案中选择一种方案。

请你返回吃掉所有 n 个橘子的最少天数。

示例 1:

输入:n = 10

输出:4

解释:你总共有 10 个橘子。

第 1 天:吃 1 个橘子,剩余橘子数 10 - 1 = 9。

第 2 天:吃 6 个橘子,剩余橘子数 9 - 2*(9/3) = 9 - 6 = 3。(9 可以被 3 整除)

第 3 天:吃 2 个橘子,剩余橘子数 3 - 2*(3/3) = 3 - 2 = 1。

第 4 天:吃掉最后 1 个橘子,剩余橘子数 1 - 1 = 0。

你需要至少 4 天吃掉 10 个橘子。

示例 2:

输入:n = 6

输出:3

解释:你总共有 6 个橘子。

第 1 天:吃 3 个橘子,剩余橘子数 6 - 6/2 = 6 - 3 = 3。(6 可以被 2 整除)

第 2 天:吃 2 个橘子,剩余橘子数 3 - 2*(3/3) = 3 - 2 = 1。(3 可以被 3 整除)

第 3 天:吃掉剩余 1 个橘子,剩余橘子数 1 - 1 = 0。

你至少需要 3 天吃掉 6 个橘子。

示例 3:

输入:n = 1

输出:1

示例 4:

输入:n = 56

输出:6

提示:

1 <= n <= 2*109

分类讨论

具有如下性质:

性质一:如果n>=3,则不可能全部是方案一,必定有方案二或方案三。当只有三个桔子时,采用方案三,只需要2天;全部全部使用方案一,则需要3天。

性质二:如 n>=4 ,且没有使用方案三或先使用方案二。则必定在n/22处采用方案二。反证法:假定某一方案,在j2个桔子时,首先使用方案二,j < n/2 假定一 。 n → \rightarrown/22 和j→ \rightarrow 0完全一样,所以只讨论:n/22 → \rightarrow j。

n/2 ⋆ \star 2 → \rightarrow n/2 → \rightarrow j ,最多用了:1+ (n/2) - j 天。式子一

n/2 ⋆ \star 2 → \rightarrow 2j → \rightarrow j 用了 n-2j+1 = n/2-j+ 1+(n/2)-j 式子二
式子二减去式子一:n/2- j 根据假定一,大于0。故:必定在n/2
2处采用方案二。

性质三:如果n >=6。且没有使用方案二或先使用方案三,则必定n/3*3出采用方案三。证明类似。

代码

核心代码

class Solution {
public:
  int minDays(int n) {
    m_data[1] = 1;
    m_data[2] = 2;
    m_data[3] = 2;
    return Rec(n);
  }
  int Rec(int n)
  {
    if (m_data.count(n))
    {
      return m_data[n];
    }
    return m_data[n] = min(Rec(n / 2 ) +n %2 +1 , Rec(n / 3)+  1 +  n %3 );
  }
  unordered_map<int, int> m_data;
};

测试用例

template<class T>
void Assert(const T& t1, const T& t2)
{
  assert(t1 == t2);
}
template<class T>
void Assert(const vector<T>& v1, const vector<T>& v2)
{
  if (v1.size() != v2.size())
  {
    assert(false);
    return;
  }
  for (int i = 0; i < v1.size(); i++)
  {
    Assert(v1[i], v2[i]);
  }
}
int main()
{ 
  
  {
    Solution sln;
    vector<int> in = { 1,2,3,4,5,6,10,2000000000 };
    vector<int> ans = { 1,2,2,3,4,3 ,4,32};
    vector<int> res(in.size());
    for (int i = 0; i < in.size(); i++)
    {
      res[i] = sln.minDays(in[i]);
    }
    Assert(res, ans);
  }
}

2023年2月

class Solution {

public:

int minDays(int n) {

if( n < 3 )

{

return n ;

}

return min( n%3 + minDays(n/3) +1 ,n%2 + minDays(n/2)+1);

}

};

2023年2月 第二版

class Solution {

public:

int minDays(int n) {

if( n < 3 )

{

return n ;

}

auto it = m_mNValue.find(n);

if( m_mNValue.end() !=it )

{

return it->second;

}

return m_mNValue[n] = min( n%3 + minDays(n/3) +1 ,n%2 + minDays(n/2)+1);

}

std::unordered_map<int,int> m_mNValue;

};

2023年7月

class Solution {

public:

int minDays(int n)

{

if (n < 3)

{

return n;

}

if (m_result.count(n))

{

return m_result[n];

}

int iRet3 = (0 == n % 3) ? (minDays(n / 3) + 1) : (minDays(n / 3 * 3) + n % 3);

int iRet2 = (0 == n % 2) ? (minDays(n / 2) + 1) : (minDays(n / 2 * 2) + n % 2);

return m_result[n] = min(iRet3, iRet2);

}

std::unordered_map<int, int> m_result;

};

2023年9月

class Solution {

public:

int minDays(int n) {

if (n < 3)

{

return n;

}

if (m_mRes.count(n))

{

return m_mRes[n];

}

int iRet = min(minDays(n / 3) + 1 + n % 3, minDays(n / 2) + 1 + n % 2);

return m_mRes[n] = iRet;

}

std::unordered_map<int, int> m_mRes;

};


相关文章
|
11月前
|
机器学习/深度学习 算法 安全
【无人机三维路径规划】基于非支配排序的鲸鱼优化算法NSWOA与多目标螳螂搜索算法MOMSA求解无人机三维路径规划研究(Matlab代码实现)
【无人机三维路径规划】基于非支配排序的鲸鱼优化算法NSWOA与多目标螳螂搜索算法MOMSA求解无人机三维路径规划研究(Matlab代码实现)
437 5
|
11月前
|
机器学习/深度学习 算法 安全
【无人机三维路径规划】多目标螳螂搜索算法MOMSA与非支配排序的鲸鱼优化算法NSWOA求解无人机三维路径规划研究(Matlab代码实现)
【无人机三维路径规划】多目标螳螂搜索算法MOMSA与非支配排序的鲸鱼优化算法NSWOA求解无人机三维路径规划研究(Matlab代码实现)
352 0
|
10月前
|
算法 数据可视化 测试技术
HNSW算法实战:用分层图索引替换k-NN暴力搜索
HNSW是一种高效向量检索算法,通过分层图结构实现近似最近邻的对数时间搜索,显著降低查询延迟。相比暴力搜索,它在保持高召回率的同时,将性能提升数十倍,广泛应用于大规模RAG系统。
813 10
HNSW算法实战:用分层图索引替换k-NN暴力搜索
|
11月前
|
存储 算法 数据可视化
基于禁忌搜索算法的TSP问题最优路径搜索matlab仿真
本程序基于禁忌搜索算法解决旅行商问题(TSP),旨在寻找访问多个城市的最短路径。使用 MATLAB 2022A 编写,包含城市坐标生成、路径优化及结果可视化功能。通过禁忌列表、禁忌长度与藐视准则等机制,提升搜索效率与解的质量,适用于物流配送、路径规划等场景。
|
11月前
|
机器学习/深度学习 数据采集 资源调度
基于长短期记忆网络定向改进预测的动态多目标进化算法(LSTM-DIP-DMOEA)求解CEC2018(DF1-DF14)研究(Matlab代码实现)
基于长短期记忆网络定向改进预测的动态多目标进化算法(LSTM-DIP-DMOEA)求解CEC2018(DF1-DF14)研究(Matlab代码实现)
462 0
|
机器学习/深度学习 并行计算 算法
MATLAB实现利用禁忌搜索算法解决基站选址问题
MATLAB实现利用禁忌搜索算法解决基站选址问题
377 0
|
存储 搜索推荐 算法
加密算法、排序算法、字符串处理及搜索算法详解
本文涵盖四大类核心技术知识。加密算法部分介绍了对称加密(如 AES)、非对称加密(如 RSA)、哈希摘要(如 SHA-2)、签名算法的特点及密码存储方案(加盐、BCrypt 等)。 排序算法部分分类讲解了比较排序(冒泡、选择、插入、归并、快排、堆排序)和非比较排序(计数、桶、基数排序)的时间复杂度、适用场景及实现思路,强调混合排序的工业应用。 字符串处理部分包括字符串反转的双指针法,及项目中用正则进行表单校验、网页爬取、日志处理的实例。 搜索算法部分详解了二分查找的实现(双指针与中间索引计算)和回溯算法的概念(递归 + 剪枝),以 N 皇后问题为例说明回溯应用。内容全面覆盖算法原理与实践
351 0
|
10月前
|
机器学习/深度学习 算法 机器人
【水下图像增强融合算法】基于融合的水下图像与视频增强研究(Matlab代码实现)
【水下图像增强融合算法】基于融合的水下图像与视频增强研究(Matlab代码实现)
802 0
|
10月前
|
数据采集 分布式计算 并行计算
mRMR算法实现特征选择-MATLAB
mRMR算法实现特征选择-MATLAB
503 2

热门文章

最新文章