本文主要是介绍【字符串】【打卡79天】leetCode每日一题:319. 灯泡开关,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
1、题目描述
初始时有 n 个灯泡处于关闭状态。第一轮,你将会打开所有灯泡。接下来的第二轮,你将会每两个灯泡关闭一个。
第三轮,你每三个灯泡就切换一个灯泡的开关(即,打开变关闭,关闭变打开)。第 i 轮,你每 i 个灯泡就切换一个灯泡的开关。直到第 n 轮,你只需要切换最后一个灯泡的开关。
找出并返回 n 轮后有多少个亮着的灯泡。
2、算法分析
1、常规方法:
定义一个boolean的数组,true代表灯亮的,false表示熄灭。默认全是亮着的。
每间隔i个就切换开关。可以使用两个for循环控制。
最后统计数组中为true的个数。
但是最后有一个999999这个用例过不去。有点可惜。
2、比较吊的方法,就一行代码,数学推理。也好理解。
知识补充:什么是因子?
假如整数n除以m,结果是无余数的整数,那么我们称m就是n的因子。因子是整数中的概念。一个整数n的因子数为包含它自身的所有因子个数。例如,12的因子数为6(1,2,3,4,6,12)。
初始有n个灯泡关闭。第i轮的操作是每i个灯泡切换一次开关(开->闭,闭->开),即切换i的倍数位置的开关。
求n轮后亮着的灯泡?
(1)第i轮时,被切换的灯泡位置是i的倍数。
(2)由(1)得出,对于第p个灯泡来说,只有其第“因子”轮才会切换,若其有q个因子,则最终被切换q次。因为初始状态是关闭状态,那么因子数是奇数的灯泡最终是亮着的。
(3)只有平方数的因子个数不是成对出现,举例:4=1*4,2*2,其因子是1,2,4。
(4)那么题目最终转化为1~n里平方数的个数,进而转化为对n开平方根,向下取整即可。
3、代码实现
常规方法:
class Solution {public int bulbSwitch(int n) {if(n == 0){return 0;}int resCount = 0;boolean[] light = new boolean[n + 1];Arrays.fill(light,true);// 从第二个开始for(int i = 2;i <= n;i++){// 间隔着开关for(int j = i;j <= n;j += i){light[j] = !light[j];}}// 计数for(int i = 1;i <= n;i++){if(light[i]){resCount++;}}return resCount;}
}
数学推理:
import java.util.*;
class Solution {public int bulbSwitch(int n) {// 取平方根return (int) Math.floor(Math.sqrt(n));}
}
这篇关于【字符串】【打卡79天】leetCode每日一题:319. 灯泡开关的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!