枚举运用的地方:
1,基于逐个尝试答案的一种问题解决策略
2,找不到数学公式
eg:求小于N的最大素数,找不到数学公式,根据n进行计算素数。
枚举
完美立方
题目:
输出样例:
思路:
1,需要把所有的数字进行尝试一边
2,确定范围
3,for循环遍历
//1,进行一个一个尝试的去试
//2,把一些不会是答案的进行排除。——确定范围
// b<=c<=d 都小于N=100
//a [2,N] b[2,a-1] c[b,a-1] d[c,a-1]
#include <iostream>
#include <cstdio>
using namespace std;
int main( ){
int n;
scanf("%d",&n);//输出一个n
int a , b , c , d;
for(int a = 2;a <= n ; a++)
for(int b = 2;b <= a-1 ; b++)
for(int c = b;c <= a-1;c++)
for(int d = c;d <= a-1;d++)
if(a*a*a == b*b*b + c*c*c + d*d*d)
printf("Cube = %d,Triple =(%d,%d,%d)\n",a,b,c,d);
return 0;
}
生理周期
思路:
1,从d+1天一直试到20252天 所以使用枚举 设相距k天
2,(k - p) % 23 == 0 && (k - e) % 28 == 0 && (k - i)%33 == 0
//1,输入p,e,i,d 情感 智力 体力 d为距离下一次出现在同一天的日子,要求输入的日子都小于365总日子小于21252
//2,输出下一次相距的日子
//思路:从d+1天一直试到20252天 所以使用枚举 设相距k天
///(k - p) % 23 == 0 && (k - e) % 28 == 0 && (k - i)%33 == 0
#include <iostream>
#include <cstdio>
using namespace std;
#define N 21252;
int main( ){
int p,e,i,d,casenum = 0;
while(cin >> p >> e >> i >> d && p!= -1){
++casenum;
int k;
for(k = d + 1;(k-p)%23;++k);
for(;(k-e)%28;k+=23);
for(;(k-i)%33;k+=23*28);
cout << "Case:"<<casenum<< "the next triple peak occurs in "<< k - d<<"days";
}
return 0;
}
称硬币
题目:
输入与输出
代码:
//思路:先假设一个硬币是轻的,看符合不符合结果,不符合在假设它是不是重的,看符合不符合称量结果,把所有的硬币都试一遍
#include <iostream>
#include <cstring>
//ABCD EFGH even
using namespace std;
char Left[3] [7];//12/2=6最多放6个
char Right [3] [7];
char result [3] [7];//存在三组数据而且每组数据最多只能有6个字母
bool isFake(char c,bool light){//c表示为假币 light为轻的
for(int i = 0;i < 3; i++){
char * pLeft,* pRight;//指向天平两边的字符串
if(light){//假币轻的话
pLeft = Left[i];
pRight = Right[i];
}
else{//假币重的话,进行左右对换
pLeft = Right[i];
pRight = Left[i];
}
switch(result[i][0]){//天平右边的情况
case 'u'://右边高
if(strchr(pRight,c)== NULL)
return false;
break;
case'e'://相等的话
if(strchr(pRight,c)||strchr(pLeft,c))
return false;
break;
case 'd'://右边低
if(strchr(pLeft,c)== NULL)
return false;
break;
}
}
return true;
}
int main()
{
int t;
cin>>t;
while(t--){
for(int i = 0;i < t; i++){
cin>>Left[i]>>Right[i]>>result[i];//ABCD EFGH even
for(char c= 'A';c <='L';c++){
if(isFake(c,true)){//c为假币且为轻的的话为true
cout<<c<"is the counterfeit coin and it is light.\n";
break;
}
else if(isFake(c,false)){//c为假币但是c为重的
cout<<c<<"is the counterfeit coin and it is heavy.\n";
break;
}
}
}
}
return 0;
}
//思路正确但有点错误
熄灯问题一
熄灯问题二
递归
递归:
1,一个函数调用其自身,就是递归
2,求 n!的递归函数
int Factorial(int n){
if(n == 0)
return 1;
else
return n * Factorial(n - 1);
}
递归和普通函数调用一样是通过栈实现的
递归的作用
1,替代多重循环
2,解决本来就用递归形式定义的问题
3,将问题分解为规模更小的子问题进行求解
汉诺塔问题
输入:盘子以及A B C
输出:盘子的动向
#include <cstdio>
#include <iostream>
using namespace std;
void hanoi(int n,char src,char mid,char dest){
if(n == 1){
printf("%c->%c",src,dest);
return ;
}
else{
hanoi(n-1,src,dest,mid);
printf("%c->%c",src,dest);
hanoi(n-1,mid,src,dest);
return;
}
}
int main( ){
int n;
scanf("%d",&n);
hanoi(n,'A','B','C');
return 0;
}
N皇后
#include <cstdio>
#include <iostream>
#include <cmath>
using namespace std;
int n;
int queenPos[100];//存放位置
void Nqueen(int k){//在0~k-1行皇后已经摆好的情况下,摆第K行以及其后的皇后
int i;
if(k==n){//k皇后已经摆好了
for(int i = 0;i<n;i++){
printf("%d",queenPos[i]+1);
return ;
}
}
for(int i = 0;i < n;i++){//逐渐尝试第K个皇后的位置
int j;
for(int j = 0;j < k;j++){
if(queenPos[j]==i||abs(queenPos[j]-i)==abs(k-j)){
break;//冲突 则进行下一个位置
}
if(j==k){//不冲突
queenPos[k]=i;
Nqueen(k+1);
}
}
}
}
int main( ){
int n;
scanf("%d",&n);
Nqueen(0);
return 0;
}//答案错误