算法竞赛入门经典: 第三章 数组和字符串 3.2开灯问题

/*
开灯问题:
有n盏等,编号为1~n。第一个人把所有灯打开,第二个人按下所有编号为2的倍数的开关(这些灯将被关掉),第三个人按下所有编号为3的倍数的开关(其中关掉的灯)
将被打开,开着的灯将被关闭,依此类推。一共有k个人,问最后有哪些灯开着?输入:n和k,输出开着的灯编号。k<=n<=1000
输入:7 3
输出:1 5 67
*/

//思路:决定一个灯开着,奇数次开,这个数能被几个数整除,设置标记数组,1表示开,0表示关

/*
关键:
1 通过memset为数组赋值,void* memset(void* buffer,int ch,size_t count)
2 iLightArr[i] = !iLightArr[i];//0,1转换不需要模2除得技巧
*/
#include <stdio.h>
#include <stdlib.h>
#include <memory.h>

#define MAXSIZE 1000 + 10

void turnOnLight(int n,int k)
{
	//int iLightArr[MAXSIZE] = {0};//初始化灯全部关闭为0
	int iLightArr[MAXSIZE];
	memset(iLightArr,0,sizeof(iLightArr));
	for(int iDivide = 1 ; iDivide <= k ; iDivide++)
	{
		for(int i = 1; i <= n ; i++)
		{
			if(i % iDivide == 0)
			{
				//iLightArr[i] = (iLightArr[i] + 1) %2;
				iLightArr[i] = !iLightArr[i];//0,1转换不需要模2除得技巧
			}
		}
	}
	for(int i = 1 ; i <= n ; i++)
	{
		if(iLightArr[i]==1)
		{
			printf("%d ",i);
		}
	}
}

int main(int argc,char* argv[])
{
	int n,k;
	scanf("%d %d",&n,&k);
	turnOnLight(n,k);
	system("pause");
	return 0;
}

你可能感兴趣的:(算法竞赛入门)