码迷,mamicode.com
首页 > 编程语言 > 详细

23-语言入门-23-开灯问题

时间:2016-01-19 14:03:38      阅读:189      评论:0      收藏:0      [点我收藏+]

标签:

?
?
描述
n盏灯,编号为1~n,第1个人把所有灯打开,第2个人按下所有编号为2 的倍数的开关(这些灯将被关掉),第3 个人按下所有编号为3的倍数的开关(其中关掉的灯将被打开,开着的灯将被关闭),依此类推。一共有k个人,问最后有哪些灯开着?输入:nk,输出开着的灯编号。kn1000

输入
输入一组数据:nk
输出
输出开着的灯编号
样例输入
7 3
样例输出
1 5 6 7
?
代码:
?
#include <stdio.h>
#include <stdlib.h>

//处理数据
static void handlerData(int n,int k);
//打印结果
static void printArray(int *pArr,int len);

int main()
{
???? int n = 0;
???? int k = 0;
???? scanf("%d %d",&n,&k);
???? handlerData(n,k);
????
???? return 0;
}

//打印结果
static void handlerData(int n,int k)
{
???? int *pArr = (int*)malloc((n+1)*sizeof(int));
????
???? //赋值 1代表打开,-1代表关闭
???? int index = 0;
???? for(;index <= n;++index)
???? {
????????? pArr[index] = 1;
???? }
????
???? //每个数的倍数循环遍历-1的时候全部打开,已经在赋值的时候处理
???? int flag = 2;
???? for(;flag<=k;++flag)
???? {
????????? //倍数开关
????????? int step = 1;
????????? //临时保存倍数形成的索引
????????? int stepIndex = step*flag;
????????? //终止条件-索引都要在n范围之内
????????? while(step<=n && stepIndex<=n)
????????? {
?????????????? pArr[stepIndex] *= -1;
?????????????? ++step;
?????????????? stepIndex = step * flag;
????????? }
???? }
????
???? //输出结果
???? printArray(pArr,n+1);
????
???? free(pArr);
}

//打印结果
static void printArray(int *pArr,int len)
{
???? int index = 1;
???? for(;index <= len;++index)
???? {
????????? if(pArr[index] == 1)
????????? {
?????????????? printf("%d ",index);
????????? }
???? }
???? printf("\n");
}

?
通过1 和 *-1的形式,处理每次开关的触发,另外为了计数方便,申请了n+1长度的数组,
第一个索引位置0闲置不用。
另外在判断具体倍数的时候,没有遍历数组%当前数 == 0进行判断,而是直接使用了倍数求得索引
如此可以减少计算量。也就是说针对数组数据的访问操作,如果能够通过下标操作的,
就尽可能的不要遍历所有的数据来减少计算量。
?

23-语言入门-23-开灯问题

标签:

原文地址:http://www.cnblogs.com/sharpfeng/p/5141750.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!