当前位置: 首页 > news >正文

LeetCode算法日记 - Day 2: 快乐数、盛水最多容器

目录

1. 快乐数

1.1 题目分析

1.2 解法

1.3 代码实现

2. 盛水最多的容器

2.1 题目分析

2.2 解法

2.3 代码实现


1. 快乐数

202. 快乐数 - 力扣(LeetCode)

编写一个算法来判断一个数 n 是不是快乐数。

「快乐数」 定义为:

  • 对于一个正整数,每一次将该数替换为它每个位置上的数字的平方和。
  • 然后重复这个过程直到这个数变为 1,也可能是 无限循环 但始终变不到 1。
  • 如果这个过程 结果为 1,那么这个数就是快乐数。

如果 n 是 快乐数 就返回 true;不是,则返回 false 。

示例 1:

输入:n = 19
输出:true
解释:
12 + 92 = 82
82 + 22 = 68
62 + 82 = 100
12 + 02 + 02 = 1

示例 2:

输入:n = 2
输出:false

提示:

  • 1 <= n <= 231 - 1

1.1 题目分析

  • 操作定义:对于一个正整数 n ,x操作计算其各位数字的平方和。例如,n = 19:
    • 第一次操作:1^2 + 9^2 = 1 + 81 = 82
    • 第二次操作:8^2 + 2^2 = 64 + 4 = 68,依此类推。
  • 循环特性:重复 x 操作时,数据必然进入循环(死循环)。原因如下:
    • 设 x 操作后最大可能值为 9^2 \times 10 = 810 (因为10位数的最大值 9999999999 的平方和不超过810)。
    • 变化范围被限制在 [1, 810] 区间内。
    • 根据鸽巢原理(元素数量超过容器大小时必有重复),经过大于811次操作后,必然出现重复值,形成循环。
  • 循环类型
    • 情况一:循环固定于 1 (即 1 \to 1 \to 1 ),此时该数为快乐数。
    • 情况二:循环在其他值间发生(如 4 \to 16 \to 37 \to 58 \to 89 \to 145 \to 42 \to 20 \to 4 \cdots),但不涉及 1。
    • 两种情况互斥,因此只需检测循环是否在 1 处发生。

1.2 解法

我们可以使用快慢指针来解决,快慢指针是一种高效检测循环的方法。其原理在于:在循环序列中,快指针总会追上慢指针。

算法步骤:

a)初始化指针

  • 慢指针 slow :起始于输入数 n 。
  • 快指针 fast :起始于 x 操作一次后的值(即 bitSum(int n))

b)移动指针

  • 慢指针每次执行一次x操作:slow = bitSum(slow)
  • 快指针每次执行两次x操作:fast = bitSum(bitSum(fast))
  • 重复此过程,直到 slow 与 fast 相遇。

c)判断结果

  • 如果相遇时 slow = 1(或 fast = 1),则是快乐数。
  • 否则,不是快乐数。

d)关键函数

x操作的核心是提取一个数$n$的各位数字并计算平方和。方法如下:

  • 初始化临时变量 int sum  = 0,int t = 0;
  • 循环操作:
    • 提取个位数字:t = n %10
    • 累加平方:sum += t*t 
    • 更新 n:n = n / 10(整数除法)
  • 当 n = 0 时停止,返回 sum。

1.3 代码实现

以下是 Java 的代码实现

class Solution {public int bitSum(int n){int sum = 0;while(n>0){int t = n%10;sum += t*t;n = n/10;}return sum;}public boolean isHappy(int n) {int slow = n;int fast = n;while(true){slow = bitSum(slow);fast = bitSum(bitSum(fast));if(slow == fast){break;}}if(slow == 1){return true;}else{return false;}}
}

2. 盛水最多的容器

11. 盛最多水的容器 - 力扣(LeetCode)

给定一个长度为 n 的整数数组 height。有 n 条垂线,第 i 条线的两个端点是 ( i , 0 ) 和 ( i ,height[i] ) 。

找出其中的两条线,使得它们与 x 轴共同构成的容器可以容纳最多的水。

返回容器可以储存的最大水量。i n

说明:你不能倾斜容器。

2.1 题目分析

在解决容器最大容积问题时,给定一个数组 height ,其中 height[i] 表示位置$i$处柱子的高度,目标是找到两个柱子,使它们与 x 轴形成的容器能容纳最多的水。容器的容积由宽度(索引差)和高度(较小柱子高度)决定。对撞指针算法通过双指针高效枚举可能解,避免不必要的计算。

2.2 解法

  1. 初始化指针

    • left指针指向数组起始位置(索引0),right指针指向数组末尾位置(索引len(height)-1)。
    • 初始化最大容积max_area = 0
  2. 指针移动逻辑

    • 计算当前容积:int v = Math.min(height[left],height[right])*(right-left);
    • 更新体积为当前最大值。设体积 ret = Math.max(ret,v);
    • 关键决策:比较 height[left] 和 height[right] :
      • 若 height[left]<height[right] ,则移动左指针 left++。
        • 原因:较小高度限制了容积。移动较小边界(左边界)可能遇到更高柱子,从而增大容积;而移动右边界只会减小宽度,受限于当前最矮的柱子,只能体积减小。
      • 否则 height[left]>height[right]  ,移动右指针 right-- 。
        • 原因:类似逻辑,移动较小边界(右边界)可能增大容积。
    • 重复以上过程,直到 left >= right。
  3. 终止条件

    • 当 left  和 right 相遇时,所有有效组合已枚举完毕,返回 ret。

2.3 代码实现

class Solution {public int maxArea(int[] height) {int left = 0, right = height.length-1,ret = 0;while(left<right){int v = Math.min(height[left],height[right])*(right-left);ret = Math.max(ret,v);if(height[left]<height[right]) left++;else right--;}return ret;}
}

http://www.dtcms.com/a/315757.html

相关文章:

  • 力扣经典算法篇-43-全排列(经典回溯问题)
  • vite面试题及详细答案120题(01-30)
  • 普通树状数组
  • 《Node.js与 Elasticsearch的全文搜索架构解析》
  • Leetcode 13 java
  • 2025-08-05Gitee + PicGo + Typora搭建免费图床
  • MongoDB学习专题(二)核心操作
  • MongoDB 从3.4.0升级到4.0.0完整指南实战-优雅草蜻蜓I即时通讯水银版成功升级-卓伊凡|bigniu
  • 时序数据库flux aggregateWindow命令详解
  • Baumer相机如何通过YoloV8深度学习模型实现道路场所路人口罩的检测识别(C#代码UI界面版)
  • 概率论之条件概率
  • ubuntu自动重启BUG排查指南
  • C++ - 仿 RabbitMQ 实现消息队列--服务端核心模块实现(六)
  • Go 单元测试:如何只运行某个测试函数(精确控制)
  • C++ 网络编程入门:TCP 协议下的简易计算器项目
  • 【STM32】HAL库中的实现(四):RTC (实时时钟)
  • 日语学习-日语知识点小记-构建基础-JLPT-N3阶段(14):文法:ていく+きた+单词
  • MQTT学习
  • Starrocks 关于 trace 命令的说明
  • C# --- 本地缓存失效形成缓存击穿触发限流
  • 【面向对象】面向对象七大原则
  • 【乐企板式文件生成工程】关于乐企板式文件(PDF/OFD/XML)生成工程介绍
  • [2401MT-B] 面积比较
  • 翻译的本质:人工翻译vs机器翻译的核心差异与互补性
  • Starrocks中的 Query Profile以及explain analyze及trace命令中的区别
  • MySQL 中 VARCHAR 和 TEXT 的区别
  • 智慧酒店:科技赋能下的未来住宿新体验
  • Spring-rabbit使用实战六
  • 国产三防平板电脑是什么?三防平板推荐
  • Spark内核调度