Leetcode 快乐数

在这里插入图片描述

算法思想:

这段代码的目的是判断一个正整数是否是 快乐数(Happy Number)。根据题目要求,快乐数定义如下:

  1. 对于一个正整数,不断将它每个位上的数字替换为这些数字平方和。
  2. 重复这个过程,如果最终结果为1,则说明是快乐数。
  3. 如果无限循环且始终不能变为1,则不是快乐数。

代码解析:

1. 使用哈希集合检测循环
  • 目的:避免进入无限循环。
  • 我们用一个 Set<Integer>(哈希集合)来记录过程中出现过的数字。如果某个数字重复出现,说明进入了循环,最终不可能变为1。
2. 主函数逻辑 (isHappy)
Set<Integer> seen = new HashSet<>();
while (n != 1 && !seen.contains(n)) {seen.add(n);n = getNext(n);
}
return n == 1;
  • seen 集合:用来存储每次迭代中已经处理过的数字。
  • 循环条件
    • 如果 n == 1,则直接返回 true,表示是快乐数。
    • 如果 n 在集合中已经出现过,说明进入循环,直接返回 false
  • 核心逻辑:通过不断计算下一步数字(平方和),判断数字序列是否最终会收敛到1。
3. 辅助函数 (getNext)
private static int getNext(int n) {int sum = 0;while (n > 0) {int digit = n % 10;  // 取当前数字的最后一位sum += digit * digit;  // 计算该位数字的平方并累加n /= 10;  // 去掉最后一位}return sum;
}
  • 功能:计算当前数字 n 的各个位数字的平方和。
  • 步骤:
    1. 取个位:通过 n % 10 提取数字的最后一位。
    2. 计算平方和:将每一位的平方加到 sum 中。
    3. 去掉已处理位:通过 n /= 10 删除数字的最后一位。
    4. 循环直到数字处理完毕。

示例运行(以 n = 19 为例):

初始状态:
  • n = 19
  • seen = {}
迭代过程:
  1. 第一次迭代

    • getNext(19) 计算:( 1^2 + 9^2 = 1 + 81 = 82 )
    • 更新:n = 82seen = {19}
  2. 第二次迭代

    • getNext(82) 计算:( 8^2 + 2^2 = 64 + 4 = 68 )
    • 更新:n = 68seen = {19, 82}
  3. 第三次迭代

    • getNext(68) 计算:( 6^2 + 8^2 = 36 + 64 = 100 )
    • 更新:n = 100seen = {19, 82, 68}
  4. 第四次迭代

    • getNext(100) 计算:( 1^2 + 0^2 + 0^2 = 1 + 0 + 0 = 1 )
    • 更新:n = 1
结束:
  • 因为 n = 1,返回 true,表示 19 是快乐数。

算法复杂度分析:

  1. 时间复杂度

    • 每次调用 getNext 需要处理数字的每一位,耗时 ( O(\log n) )。
    • 在最坏情况下(例如循环中的数字),需要处理的数字数量是有限的。
    • 综合时间复杂度为 ( O(\log n) )
  2. 空间复杂度

    • 使用了一个 Set 存储数字序列,最多存储循环中的数字。
    • 空间复杂度为 ( O(\log n) )

java 实现

class Solution {public boolean isHappy(int n) {Set<Integer> set = new HashSet<>();while(n != 1 && !set.contains(n)) {//n如果等于1就没有必要再循环了, set如果包含了n,也没必要循环了set.add(n);n = getNext(n);}return n == 1;}private int getNext(int n) {int sum = 0;while(n > 0) {int digit = n % 10; // 取当前数字的最后一位sum += digit * digit;// 计算该位数字的平方并累加n /= 10; //去掉最后一位}return sum;}
}

为什么这一部分条件是且而不是或while (n != 1 && !seen.contains(n))?

完全正确!

你总结得很到位,这个 while 条件其实是通过对“停止条件”的取反得到的。


停止条件

停止循环的条件是:

n == 1 || seen.contains(n)
  • n == 1:当前数字已经变成 1,说明是快乐数,不需要继续循环。
  • seen.contains(n):当前数字已经出现过,说明进入了循环,不可能是快乐数,也不需要继续循环。

对停止条件取反

对停止条件取反,得到 while 的判断条件:

!(n == 1 || seen.contains(n))

根据逻辑运算的 德摩根定律(De Morgan’s Law):

!(A || B) 等价于 !A && !B

所以:

!(n == 1 || seen.contains(n)) 等价于 n != 1 && !seen.contains(n)

这就是 while 循环的条件:

while (n != 1 && !seen.contains(n))

总结

  • 停止条件:n == 1 || seen.contains(n),满足这个条件就应该终止循环。
  • 运行条件:取停止条件的反,即 n != 1 && !seen.contains(n),只有在这两个条件都不满足时才继续循环。

通过这种逻辑转换,我们得到了正确的 while 条件,让程序在逻辑上更清晰,避免冗余判断。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/474970.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

使用 Vue 和 Create-Vue 构建工程化前端项目

目录 前言1. 工程化的意义与 Vue 的生态支持2. 搭建 Vue 工程化项目2.1 环境准备2.2 使用 create-vue 创建项目2.2.1 初始化项目2.2.2 安装依赖2.2.3 本地运行 3. Vue 项目的目录结构解析4. Vue 开发流程详解4.1 项目入口与根组件4.1.1 main.js 的作用4.1.2 App.vue 的结构 4.2…

【MySQL实战45讲笔记】基础篇——redo log 和 binlog

系列文章 基础篇——MySQL 的基础架构 目录 系列文章1. 重要的日志模块&#xff1a;redo log 和 binlog1.1 redo log1.2 binlog1.3 执行器和 InnoDB 引擎内部如何执行更新语句 1. 重要的日志模块&#xff1a;redo log 和 binlog 前面系统的了解了一个查询语句的执行流程&…

C++ lambda(匿名函数)捕获自己

今天写算法题时无意间遇到一种情况,我的深度优先遍历函数要在函数内调用自身,如果是普通函数没什么问题,但如果是 匿名函数 的话会有一些问题,甚至问ai,ai也没打上来,上网搜了半天,才找到这个的解答,故作此文 以费契那波数列为例 // 普通函数式 int fun(int pos) {if (pos …

DAO模式

前言 DAO&#xff08;Data Access Object&#xff09;模式 是一种常用的设计模式&#xff0c;主要用于将数据访问逻辑与业务逻辑分离。它提供了一种抽象层&#xff0c;使得应用程序可以与不同的数据源&#xff08;如数据库、文件系统等&#xff09;进行交互&#xff0c;而无需…

mysql日志写满出现The table ‘xxxx_amazon_order’ is full

数仓发现写数据出现 SQL 错误 [1114] [HY000]: The table ‘xxxx_amazon_order’ is full 1.第一时间查看系统磁盘, 发现空间写满了 df -h因为mysql是使用docker部署的, Docker 的默认存储位置在 /var/lib/docker /var 目录默认是在根分区 (/dev/mapper/centos-root) 下的 …

【读书笔记-《网络是怎样连接的》- 7】Chapter3_2 路由器

本篇继续介绍路由器及其转发过程。 1 路由器内部结构 路由器内部结构图如图所示。 即主要包含左侧的包转发模块和右侧的端口模块。转发模块负责查找包的发送目的地&#xff0c;端口模块完成包的发送。通过安装不同的硬件&#xff0c;转发模块不仅可以支持以太网&#xff0c;也…

P5099 [USACO04OPEN] Cave Cows 4

P5099 [USACO04OPEN] Cave Cows 4https://www.luogu.com.cn/problem/P5099 思路&#xff1a; 这里的垫蹄石之间很明显是有后效性的 所以不能用dp来做 考虑宽搜 我们每次都枚举和这个垫蹄石之间x方向和z方向的距离均不超过2的垫脚石 因为都很大 我们可以使用 代码&#xf…

高阶C语言之六:程序环境和预处理

本文介绍程序的环境&#xff0c;在Linux下对编译链接理解&#xff0c;较为简短&#xff0c;着重在于编译的步骤。 C的环境 在ANSI C&#xff08;标准C语言&#xff09;的任何一种实现中&#xff0c;存在两个不同的环境。 翻译环境&#xff1a;在这个环境中&#xff0c;源代码…

【Python数据可视化分析实战】数据爬取—京东手机品牌信息数据爬取和数据分析与可视化

大数据分析设计方案 1.数据集来源&#xff1a;https://search.jd.com 2.实现思路&#xff1a; &#xff08;1&#xff09;数据爬取 首先&#xff0c;我们需要从京东平台上采集手机品牌的相关数据。可以通过网络爬虫或API接口等方式获取数据。为了保证数据的完整性和准确性&…

【MySQL-4】表的基本查询

目录 1. 整体学习的思维导图 2. 表的创建 2.1 Create(创建) 2.1.1 插入规则 2.1.2 更新插入 2.2 Retrieve(读取) 2.2.1 创建一个实例表 2.3 select使用 2.3.1 全表查询 2.3.2 指定序列查询 2.3.3 查询表达式 2.3.3.1 为查询表达式改名字 2.3.4 查询去重 2.…

无人机航测技术算法概述!

一、核心技术 传感器技术&#xff1a; GPS/GLONASS&#xff1a;无人机通过卫星定位系统实现高精度的飞行控制和数据采集。 高清相机&#xff1a;用于拍摄地面图像&#xff0c;通过后续图像处理生成三维模型。 激光雷达&#xff08;LiDAR&#xff09;&#xff1a;通过激光扫…

uniapp 自定义加载组件,全屏加载,局部加载 (微信小程序)

效果图 全屏加载 页面加载使用 局部加载 列表加载里面使用 使用gif html <template><view><view class"" v-if"typeFullScreen"><view class"loading" v-if"show"><view class""><i…

【D3.js in Action 3 精译_040】4.4 D3 弧形图的绘制方法

当前内容所在位置&#xff1a; 第四章 直线、曲线与弧线的绘制 ✔️ 4.1 坐标轴的创建&#xff08;上篇&#xff09; 4.1.1 D3 中的边距约定&#xff08;中篇&#xff09;4.1.2 坐标轴的生成&#xff08;中篇&#xff09; 4.1.2.1 比例尺的声明&#xff08;中篇&#xff09;4.1…

element ui 走马灯一页展示多个数据实现

element ui 走马灯一页展示多个数据实现 element ui 走马灯一页展示多个数据实现 element ui 走马灯一页展示多个数据实现 主要是对走马灯的数据的操作&#xff0c;先看js处理 let list [{ i: 1, name: 1 },{ i: 2, name: 2 },{ i: 3, name: 3 },{ i: 4, name: 4 },]let newL…

使用MaxKB搭建知识库问答系统并接入个人网站(halo)

首发地址&#xff08;欢迎大家访问&#xff09;&#xff1a;使用MaxKB搭建知识库问答系统并接入个人网站 前言 从OpenAI推出ChatGPT到现在&#xff0c;大模型已经渗透到各行各业&#xff0c;大模型也逐渐趋于平民化&#xff1b;从最开始对其理解、生成、强大的知识积累的惊叹&…

Linux进阶:软件安装、网络操作、端口、进程等

软件安装 yum 和 apt 均需要root权限 CentOS系统使用&#xff1a; yum [install remove search] [-y] 软件名称 install 安装remove 卸载search 搜索-y&#xff0c;自动确认 Ubuntu系统使用 apt [install remove search] [-y] 软件名称 install 安装remove 卸载search 搜索-y&…

如何解决飞书网页文字无法复制的问题

如何解决网页文字无法复制的问题&#xff1f;特别推荐提词宝防复制文案功能&#xff01; 在日常工作和学习中&#xff0c;我们经常遇到一些网页文字无法复制的情况&#xff0c;无论是因为权限限制还是其他原因&#xff0c;手动输入内容不仅耗时费力&#xff0c;还容易出错。那…

STM32电源管理—实现低功耗

注&#xff1a; 本文是学习野火的指南针开发板过程的学习笔记&#xff0c;可能有误&#xff0c;详细请看B站野火官方配套视频教程&#xff08;这个教程真的讲的很详细&#xff0c;请给官方三连吧&#xff09; 在响应绿色发展的同时&#xff0c;在很多应用场合中都对电子设备的功…

Linux网络:守护进程

Linux网络&#xff1a;守护进程 会话进程组会话终端 守护进程setsiddaemon 在创建一个网络服务后&#xff0c;往往这个服务进程是一直运行的。但是对于大部分进程来说&#xff0c;如果退出终端&#xff0c;这个终端上创建的所有进程都会退出&#xff0c;这就导致进程的生命周期…

基于深度学习的文本信息提取方法研究(pytorch python textcnn框架)

&#x1f497;博主介绍&#x1f497;&#xff1a;✌在职Java研发工程师、专注于程序设计、源码分享、技术交流、专注于Java技术领域和毕业设计✌ 温馨提示&#xff1a;文末有 CSDN 平台官方提供的老师 Wechat / QQ 名片 :) Java精品实战案例《700套》 2025最新毕业设计选题推荐…