|
| 1 | +### 题目描述 |
| 2 | + |
| 3 | +这是 LeetCode 上的 **[319. 灯泡开关](https://leetcode-cn.com/problems/bulb-switcher/solution/gong-shui-san-xie-jing-dian-shu-lun-tui-upnnb/)** ,难度为 **中等**。 |
| 4 | + |
| 5 | +Tag : 「数学」 |
| 6 | + |
| 7 | + |
| 8 | + |
| 9 | +初始时有 `n` 个灯泡处于关闭状态。第一轮,你将会打开所有灯泡。接下来的第二轮,你将会每两个灯泡关闭一个。 |
| 10 | + |
| 11 | +第三轮,你每三个灯泡就切换一个灯泡的开关(即,打开变关闭,关闭变打开)。 |
| 12 | + |
| 13 | +第 `i` 轮,你每 `i` 个灯泡就切换一个灯泡的开关。直到第 `n` 轮,你只需要切换最后一个灯泡的开关。 |
| 14 | + |
| 15 | +找出并返回 `n` 轮后有多少个亮着的灯泡。 |
| 16 | + |
| 17 | +示例 1: |
| 18 | + |
| 19 | +``` |
| 20 | +输入:n = 3 |
| 21 | + |
| 22 | +输出:1 |
| 23 | + |
| 24 | +解释: |
| 25 | +初始时, 灯泡状态 [关闭, 关闭, 关闭]. |
| 26 | +第一轮后, 灯泡状态 [开启, 开启, 开启]. |
| 27 | +第二轮后, 灯泡状态 [开启, 关闭, 开启]. |
| 28 | +第三轮后, 灯泡状态 [开启, 关闭, 关闭]. |
| 29 | + |
| 30 | +你应该返回 1,因为只有一个灯泡还亮着。 |
| 31 | +``` |
| 32 | +示例 2: |
| 33 | +``` |
| 34 | +输入:n = 0 |
| 35 | + |
| 36 | +输出:0 |
| 37 | +``` |
| 38 | +示例 3: |
| 39 | +``` |
| 40 | +输入:n = 1 |
| 41 | + |
| 42 | +输出:1 |
| 43 | +``` |
| 44 | + |
| 45 | +提示: |
| 46 | +* 0ドル <= n <= 10^9$ |
| 47 | + |
| 48 | +--- |
| 49 | + |
| 50 | +### 数学 |
| 51 | + |
| 52 | +这是一道经典的数论题。 |
| 53 | + |
| 54 | +整理一下题意:**第 $i$ 轮改变所有编号为 $i$ 的倍数的灯泡的状态(其中灯泡编号从 1ドル$ 开始)。** |
| 55 | + |
| 56 | +**一个编号为 $x$ 的灯泡经过 $n$ 轮后处于打开状态的充要条件为「该灯泡被切换状态次数为奇数次」。** |
| 57 | + |
| 58 | +同时,一个灯泡切换状态的次数为其约数的个数(去重)。 |
| 59 | + |
| 60 | +于是问题转换为:**在 $[1,n]$ 内有多少个数,其约数的个数为奇数**。这些约数个数为奇数的灯泡就是最后亮着的灯泡。 |
| 61 | + |
| 62 | +又根据「约数」的定义,我们知道如果某个数 $k$ 为 $x$ 的约数,那么 $\frac{x}{k}$ 亦为 $x$ 的约数,即「约数」总是成对出现,那么某个数的约数个数为奇数,意味着某个约数在分解过程中出现了 2ドル$ 次,且必然重复出现在同一次拆解中,即 $k = \frac{x}{k},ドル即有 $x$ 为完全平方数(反之亦然)。 |
| 63 | + |
| 64 | +问题最终转换为:**在 $[1,n]$ 中完全平方数的个数为多少。** |
| 65 | + |
| 66 | +根据数论推论,$[1,n]$ 中完全平方数的个数为 $\left \lfloor \sqrt{n} \right \rfloor,ドル即最后亮着的灯泡数量为 $\left \lfloor \sqrt{n} \right \rfloor$。 |
| 67 | + |
| 68 | +代码: |
| 69 | +```Java |
| 70 | +class Solution { |
| 71 | + public int bulbSwitch(int n) { |
| 72 | + return (int)Math.sqrt(n); |
| 73 | + } |
| 74 | +} |
| 75 | +``` |
| 76 | +* 时间复杂度:$O(1)$ |
| 77 | +* 空间复杂度:$O(1)$ |
| 78 | + |
| 79 | +--- |
| 80 | + |
| 81 | +### 最后 |
| 82 | + |
| 83 | +这是我们「刷穿 LeetCode」系列文章的第 `No.319` 篇,系列开始于 2021年01月01日,截止于起始日 LeetCode 上共有 1916 道题目,部分是有锁题,我们将先把所有不带锁的题目刷完。 |
| 84 | + |
| 85 | +在这个系列文章里面,除了讲解解题思路以外,还会尽可能给出最为简洁的代码。如果涉及通解还会相应的代码模板。 |
| 86 | + |
| 87 | +为了方便各位同学能够电脑上进行调试和提交代码,我建立了相关的仓库:https://github.com/SharingSource/LogicStack-LeetCode。 |
| 88 | + |
| 89 | +在仓库地址里,你可以看到系列文章的题解链接、系列文章的相应代码、LeetCode 原题链接和其他优选题解。 |
| 90 | + |
0 commit comments