首页 > 其他分享 >暴力枚举1-循环枚举

暴力枚举1-循环枚举

时间:2022-12-09 00:00:45浏览次数:64  
标签:10 暴力 int long 枚举 循环 go 思路

暴力枚举

一.循环枚举

例题1

​ 可以通过枚举点的坐标来计算长方形和正方形的个数

普通思路:

​ 枚举所有可能性(通过枚举):

int main()
{
	int n,m,squ=0,rec=0;
	cin>>n>>m;
	for(int i=1;i<=n;i++){
		for(int j=1;j<=m;j++){   //枚举左上角的点 
			for(int k=i+1;k<=n+1;k++){  
				for(int z=j+1;z<=m+1;z++){     //枚举右下角的点 
					if((k-i)==(z-j)){          //满足条件就++ 
						squ++;
					}else{
						rec++;
					}
				}
			}
		}
	}
	cout<<squ<<" "<<rec;
	return 0;
}

​ 该代码可以得出正确答案,可是会TLE,时间复杂度为O(m2n2),考虑新的枚举策略。

思路一:减少枚举量

​ 枚举一个点,统计以这个点为顶点的方形数量,再除4(每个方形被算了4遍) ,注意long long类型。

int main()
{
	int n,m;
	long long squ=0,rec=0;
	cin>>n>>m;
	for(int i=0;i<=n;i++){   //枚举平面每一个点 
		for(int j=0;j<=m;j++){
			long long t=min(j,i)+min(j,n-i)+min(m-j,i)+min(m-j,n-i);
			squ+=t;
			rec+=n*m-t;
		}
	}
	squ/=4,rec/=4;
	cout<<squ<<" "<<rec<<endl;
	return 0;
}

思路二:去掉重复的情况

​ 去掉思路一的代码重复的情况。仅仅枚举方形右下角的顶点。

for(int j=0;j<=m;j++){
	long long t=min(j,i);
	squ+=t;
	rec+=i*j-t;
}

思路三:枚举其他要素

​ 如可以枚举方形的边长,枚举a*b的方形数量

for(int i=1;i<=n;i++){  //枚举方形边长 
		for(int j=1;j<=m;j++){
			if(i!=j){
				rec+=(m-j+1)*(n-i+1);   //简单分析得到公式 
			}else{
				squ+=(m-j+1)*(n-i+1);
			}
		}
	}

例题二

P2089 烤鸡

思路一:暴力

​ 可以直接写10层for循环再加一个if判断

#include <bits/stdc++.h>
using namespace std;
#define rep(i,a,b) for(int i=a;i<=b;i++)
int main()
{
	int n,cnt=0;
	cin>>n;
	if(n<10){
		cout<<"0";
	}else{
		rep(a,1,3) rep(b,1,3) rep(c,1,3) rep(d,1,3) rep(e,1,3)
		rep(f,1,3) rep(g,1,3) rep(h,1,3) rep(i,1,3) rep(j,1,3){
			if(a+b+c+d+e+f+g+h+i+j==n){
				cnt++;
			}
		}
		cout<<cnt<<endl;
		rep(a,1,3) rep(b,1,3) rep(c,1,3) rep(d,1,3) rep(e,1,3)
		rep(f,1,3) rep(g,1,3) rep(h,1,3) rep(i,1,3) rep(j,1,3){
			if(a+b+c+d+e+f+g+h+i+j==n){
				printf("%d %d %d %d %d %d %d %d %d %d\n",
						a,b,c,d,e,f,g,h,i,j);
			}
		}
	}
	return 0;
}

​ #define rep(i,a,b) for(int i=a;i<=b;i++) 是宏定义,只会做简单的字符串变换,所以使用时要勤加括号。

思路二:限定变量的范围(枚举剪枝)

​ 当ans已经超过了n,便可以不用再枚举以下的元素。

例题三

P1618 三连击(升级版)

思路:减少枚举次数

​ 可以不用枚举9个数字,只需要枚举出一个三位数,便可以通过比例确定另外两个数。

#include <bits/stdc++.h>
using namespace std;

int s[10];

void go(int x)   //分解3位数到桶里
{
	s[x%10]=1;
	s[x/10%10]=1;
	s[x/100]=1;
}

bool check(int x,int y,int z)
{
	if(z>999){    //保证三位数
		return 0;
	}
	go(x),go(y),go(z);   //保证1-9每个数都存在
	for(int i=1;i<10;i++){
		if(!s[i]){
			return 0;
		}
	}
	return 1;
}

int main()
{
	long long a,b,c,x,y,z,cnt=0;
	cin>>a>>b>>c;
	if(a==0||b==0||c==0){   //排除特殊数据
		cout<<"No!!!"<<endl;
	}
	for(x=123;x<=987;x++){   //枚举第一个三位数
		if(x*b%a||x*c%a){    //判断后两位数是否存在
			continue;
		}
		y=x*b/a;
		z=x*c/a;
		if(check(x,y,z)){      //函数判断三个数是否符合要求
			cnt++;
			cout<<x<<" "<<y<<" "<<z<<endl;
		}
		memset(s,0,sizeof(s));
	}
	if(cnt==0){
		cout<<"No!!!"<<endl;
	}
	return 0;
}

总结

​ 循环枚举可以通过如下方式优化

  1. 根据题目减少枚举量
  2. 去掉重复情况
  3. 枚举其他要素
  4. 枚举裁剪

除以上常见策略,同时也要通过做题来积累常见简化方法。

以上便是自己的一些简单的循环枚举总结

标签:10,暴力,int,long,枚举,循环,go,思路
From: https://www.cnblogs.com/Lionel-ZQY/p/16967775.html

相关文章

  • c语言分支与循环
    本题要求你写个程序把给定的符号打印成沙漏的形状。例如给定17个“*”,要求按下列格式打印***************** 所谓“沙漏形状”,是指每行输出奇数个符号;各行符......
  • 一种典型的不知循环次数的c语言循环问题
    问题如图  代码如下1#define_CRT_SECURE_NO_WARNINGS12#include<stdio.h>3intmain()4{5puts("输入正整数,以-1为结束标志\n");6intte......
  • jQuery单行循环滚动展示代码
    循环滚动展示的文字和图片每个人都见过,实现类似效果的JS也很多。但如果只用于几个条目或三五张图片,体积庞大的JS会浪费资源。看见Jinwen​同学用AdamCai的代码,感觉......
  • m基于ACO蚁群算法的考虑装载率的循环送货的最短线路规划MATLAB仿真
    1.算法概述        根据这些装载率再结合路径最短来设计几个循环送货的线路。最理想状态是一条循环路径出去把所有的货都能遍历,并且装载率也很高。但是显然理想状......
  • 循环优化一
    主角:takewhile判断序列中元素是否为偶数,奇数则终止这是我们最常用的一种方式,其实没必要这么复杂1a=[4,6,7,3]234defjudge_is_even(item):5......
  • 【js】事件循环evenloop
    先上题目console.log(1)setTimeout(()=>{console.log(2)},0)console.log(3)答案:132console.log(1)setTimeout(()=>{console.log(2)......
  • Spring如何处理循环依赖问题
    Spring如何处理循环依赖问题什么是循环依赖:就是多个bean之间相互依赖,形成了一个闭环,比如beanA需要引用BeanB,BeanB需要引用BeanA,形成循环关系。一般默认在单例模式中,属性......
  • Java流程控制(6)循环结构 while循环
             ......
  • for循环的坑——误用for循环中定义的变量
    下面这段代码输出什么,说明原因。funcmain(){ slice:=[]int{0,1,2,3} m:=make(map[int]*int) forkey,val:=rangeslice{ m[key]=&val } fork,......
  • c语言分支与循环pta练习题
    7-7高空坠球皮球从某给定高度自由落下,触地后反弹到原高度的一半,再落下,再反弹,……,如此反复。问皮球在第n次落地时,在空中一共经过多少距离?第n次反弹的高度是多少?输入格......