P34,例3-1,开灯问题,解题说明
问题描述:
有n盏灯,编号为1~n。进行如下活动过程:
第1个人把所有的灯打开;
第2个人把所有编号为2的倍数的灯关掉;
第3个人把所有编号为3的倍数的灯打开;
……
以此类推。
一共有k个人参与了上述活动。
问:最后有哪些灯是开着的?
输入:n和k。k<=n<=1000。假设用户输入的数据都是合法的。
输出:开着的灯的编号。各个编号之间用逗号隔开,第一个编号之前和最后一个编号之后的逗号可有可无。
解题策略:
本题需要描述n盏电灯的状态,所以,用一维数组来存储这n盏电灯的状态,是“很自然的”。
我们可以使用整数的一维数组:int lamps[N]; 其中每个元素的数值状态约定如下:
-1:灯暗
1:灯亮
采用这种状态约定的原因是:可以认为在第1个人开灯之前,所有的灯都是暗的。而每次开关动作,只需要将该整数×-1即可。
我们编写程序,模拟上述k个人的活动对该一维数组产生的影响,最后,输出得到的数组数据即可(只需要输出那些亮着的灯的编号)。
===================================
源代码可以从这里下载:
控制流图可以从这里下载:
===================================
源代码:
0001 /* 0002 例题3-1,开灯问题.c 0003 16:11 2011年2月2日 0004 fzd19zx@gmail.com 0005 问题描述: 0006 有n盏灯,编号为1~n。进行如下活动过程: 0007 第1个人把所有的灯打开; 0008 第2个人把所有编号为2的倍数的灯关掉; 0009 第3个人把所有编号为3的倍数的灯打开; 0010 …… 0011 以此类推。 0012 一共有k个人参与了上述活动。 0013 问:最后有哪些灯是开着的? 0014 输入:n和k。k<=n<=1000。假设用户输入的数据都是合法的。 0015 输出:开着的灯的编号。各个编号之间用逗号隔开,第一个编号之前和最后一个编号之后的逗号可有可无。 0016 解题策略: 0017 本题需要描述n盏电灯的状态,所以,用一维数组来存储这n盏电灯的状态,是“很自然的”。 0018 我们可以使用整数的一维数组:int lamps[N]; 其中每个元素的数值状态约定如下: 0019 -1:灯暗 0020 1:灯亮 0021 采用这种状态约定的原因是:可以认为在第1个人开灯之前,所有的灯都是暗的。而每次开关动作,只需要将该整数×-1即可。 0022 我们编写程序,模拟上述k个人的活动对该一维数组产生的影响,最后,输出得到的数组数据即可(只需要输出那些亮着的灯的编号)。 0023 */ 0024 # include "stdio.h" 0025 # define N (1001) 0026 int main() { 0027 int lamps[N], /*电灯;lamps[0]是用不着的存储空间*/ 0028 n, /*n盏电灯*/ 0029 k, /*k个人*/ 0030 i,j; 0031 scanf("%d%d",&n,&k); 0032 /*初始化电灯状态*/ 0033 for (i=1; i<=n; i=i+1) { 0034 lamps[i]=-1; 0035 } 0036 /*模拟活动过程: 第i个人参与活动*/ 0037 for (i=1; i<=k; i=i+1) { 0038 /*对第j盏灯进行操作*/ 0039 for (j=1; j<=n; j=j+1) { 0040 if (j%i==0) lamps[j]=lamps[j]*(-1); 0041 } 0042 } 0043 /*输出活动结果*/ 0044 for (i=1; i<=n; i=i+1) { 0045 if (lamps[i]==1) printf("%d,",i); 0046 } 0047 return 0; 0048 }