前几天有人跟我说,啊,说dfs一搜搜着搜着就把自己搜蒙了,说一写dfs就要dfs(int a,int b,int c),括号里面放一堆东西。啊今天我要澄清一下,dfs其实没有你想的那么复杂。

dfs这个玩意其实是有模板的:

//DFS模板
inline void dfs(int u){
if(u==题目中的某个条件){
按照题目要求单组输出
puts("");
return ;
}
for(register int i=___;i<___;i___){
if(!st[i]%%____________){
st[i]=true;
按照题目要求操作
回溯//e.g. dfs(u+1);
st[i]=false;//回复现场
//path[u]=0;
}
}
}

举个例子:

给定一个整数 n,将数字 1~n 排成一排,将会有很多种排列方法。

现在,请你按照字典序将所有的排列方法输出。

就这道题,我们用模板解一下

#include<bits/stdc++.h>
using namespace std;
int n;
int path[10000];
bool st[10000];
inline void dfs(int u){
if(u==n){
for(register int i=0;i<n;i++){
cout<<path[i]<<" ";
}
puts("");
return ;
}
for(register int i=0;i<n;i++){
if(!st[i]){
st[i]=true;
path[u]=i+1;
dfs(u+1);
st[i]=false;
path[u]=0;
}
}
}
int main(){
cin>>n;
dfs(0);
return 0;
}

你看,轻轻松松,那有人问了,每道题都能这么解吗???万一要dfs好多数呢???大部分其实只要一个数就行,我举个栗子:

n皇后问题是指将 n 个皇后放在 n×n 的国际象棋棋盘上,

使得皇后不能相互攻击到,

即任意两个皇后都不能处于同一行、同一列或同一斜线上。

现在给定整数 n,请你输出所有的满足条件的棋子摆法。

#include <iostream>

using namespace std;

const int N = 10;

int n;
bool row[N], col[N], dg[N * 2], udg[N * 2];
char g[N][N]; void dfs(int x, int y, int s)
{
if (s > n) return;
if (y == n) y = 0, x ++ ; if (x == n)
{
if (s == n)
{
for (int i = 0; i < n; i ++ ) puts(g[i]);
puts("");
}
return;
} g[x][y] = '.';
dfs(x, y + 1, s); if (!row[x] && !col[y] && !dg[x + y] && !udg[x - y + n])
{
row[x] = col[y] = dg[x + y] = udg[x - y + n] = true;
g[x][y] = 'Q';
dfs(x, y + 1, s + 1);
g[x][y] = '.';
row[x] = col[y] = dg[x + y] = udg[x - y + n] = false;
}
} int main()
{
cin >> n; dfs(0, 0, 0); return 0;
}

大部分人肯定这么做的,但是,你用初中数学算一算,就可以进行改进:

#include<bits/stdc++.h>
using namespace std;
const int N=3e3;
int n;
char g[N][N];
bool col[N],dg[N],udg[N];
void dfs(int u){
if(u==n){
for(int i=0;i<n;i++){
for(int j=0;j<n;j++)
cout<<g[i][j];
cout<<endl;
}
puts("");
return;
}
for(int i=0;i<n;i++)
if(!col[i]&&!dg[u+i]&&!udg[n-u+i]){
g[u][i]='Q';
col[i]=dg[u+i]=udg[n-u+i]=true;
dfs(u+1);
col[i]=dg[u+i]=udg[n-u+i]=false;
g[u][i]='.';
}
}
int main(){
cin>>n;
for(int i=0;i<n;i++)
for(int j=0;j<n;j++)
g[i][j]='.';
dfs(0);
return 0;
}

效果是一样的,但是不需要去想dfs后面要几个数,

dfs(int u)

这一个就够了啊

当然,在图中的dfs也是这个道理。

给定一颗树,树中包含 n 个结点(编号 1~n)和 n-1 条无向边。

请你找到树的重心,并输出将重心删除后,剩余各个连通块中点数的最大值。

重心定义:重心是指树中的一个结点,如果将这个点删除后,剩余各个连通块中点数的最大值最小,那么这个节点被称为树的重心。

输入格式
第一行包含整数 n,表示树的结点数。 接下来 n+1 行,每行包含两个整数 a 和 b,表示点 a 和点 b 之间存在一条边。 输出格式
输出一个整数 m,表示将重心删除后,剩余各个连通块中点数的最大值。 #include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm> using namespace std; const int N = 100010, M = N * 2; int n;
int h[N], e[M], ne[M], idx;
int ans = N;
bool st[N]; void add(int a, int b)
{
e[idx] = b, ne[idx] = h[a], h[a] = idx ++ ;
} int dfs(int u)
{
st[u] = true; int size = 0, sum = 0;
for (int i = h[u]; i != -1; i = ne[i])
{
int j = e[i];
if (st[j]) continue; int s = dfs(j);
size = max(size, s);
sum += s;
} size = max(size, n - sum - 1);
ans = min(ans, size); return sum + 1;
} int main()
{
scanf("%d", &n); memset(h, -1, sizeof h); for (int i = 0; i < n - 1; i ++ )
{
int a, b;
scanf("%d%d", &a, &b);
add(a, b), add(b, a);
} dfs(1); printf("%d\n", ans); return 0;
}

DFS深搜小谈的更多相关文章

  1. CodeM美团点评编程大赛初赛B轮 黑白树【DFS深搜+暴力】

    [编程题] 黑白树 时间限制:1秒 空间限制:32768K 一棵n个点的有根树,1号点为根,相邻的两个节点之间的距离为1.树上每个节点i对应一个值k[i].每个点都有一个颜色,初始的时候所有点都是白色 ...

  2. DFS 深搜专题 入门典例 -- 凌宸1642

    DFS 深搜专题 入门典例 -- 凌宸1642 深度优先搜索 是一种 枚举所有完整路径以遍历所有情况的搜索方法 ,使用 递归 可以很好的实现 深度优先搜索. 1 最大价值 题目描述 ​ 有 n 件物品 ...

  3. 【DFS深搜初步】HDOJ-2952 Counting Sheep、NYOJ-27 水池数目

    [题目链接:HDOJ-2952] Counting Sheep Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 ...

  4. DFS深搜——Red and Black——A Knight&#39;s Journey

    深搜,从一点向各处搜找到全部能走的地方. Problem Description There is a rectangular room, covered with square tiles. Eac ...

  5. Red and Black(DFS深搜实现)

    Description There is a rectangular room, covered with square tiles. Each tile is colored either red ...

  6. poj 2386:Lake Counting(简单DFS深搜)

    Lake Counting Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 18201   Accepted: 9192 De ...

  7. UVA 165 Stamps (DFS深搜回溯)

     Stamps  The government of Nova Mareterrania requires that various legal documents have stamps attac ...

  8. 解救小哈——dfs深搜

    问题描述: 小哈去玩迷宫,结果迷路了,小哼去救小哈.迷宫由n行m列的单元格组成(n和m都小于等于50),每个单元格要么是空地,要么是障碍物. 问题:帮小哼找到一条从迷宫的起点通往小哈所在位置的最短路径 ...

  9. POJ-1190-生日蛋糕-DFS(深搜)-枚举-多重剪枝

    题目链接: 这个题目非常好,有难度:能够好好的多做做: #include<iostream> #include<string> #include<cstdio> # ...

  10. PAT Advanced 1155 Heap Paths (30) [DFS, 深搜回溯,堆]

    题目 In computer science, a heap is a specialized tree-based data structure that satisfies the heap pr ...

随机推荐

  1. 【go语言】2.1.3 函数的定义和使用

    在 Go 语言中,函数是一种代码抽象和复用的方式.函数可以接受参数,执行特定的操作,并返回结果. 函数的定义 函数的定义以 func 关键字开始,后面跟着函数名.参数列表.返回值列表(可选)以及函数体 ...

  2. Postgresql: 常用配置

    允许远程链接postgresql 要允许 PostgreSQL 数据库允许远程连接,需要进行以下配置步骤: 打开 PostgreSQL 的主配置文件 postgresql.conf.通常,该文件位于以 ...

  3. 一 APPIUM基本理论知识(转)

    1.APPIUM介绍 Appium 是一个自动化测试开源工具,支持 iOS 平台和 Android 平台上的原生应用,web 应用和混合应用.所谓的"移动原生应用"是指那些用 iO ...

  4. Azure Terraform(十四)Azure Key Vault 的机密管理

    一,引言 最近有网友私信我,将 Terraform 部署到 Azure 是一种将基础结构作为代码进行管理的好方法,但是如何使用 Azure Key Vault 来存储我们的 Secret ?在这篇博文 ...

  5. Redis专题-队列

    Redis专题-队列 首先,想一想 Redis 适合做消息队列吗? 1.消息队列的消息存取需求是什么?redis中的解决方案是什么? 无非就是下面这几点: 0.数据可以顺序读取 1.支持阻塞等待拉取消 ...

  6. Unity UGUI的Image(图片)组件的介绍及使用

    UGUI的Image(图片)组件的介绍及使用 1. 什么是UGUI的Image(图片)组件? UGUI的Image(图片)组件是Unity引擎中的一种UI组件,用于显示2D图像.它提供了一种简单而灵活 ...

  7. Unity UGUI的ScrollRect(滚动视图)组件的介绍及使用

    Unity UGUI的ScrollRect(滚动视图)组件的介绍及使用 1. 什么是ScrollRect组件? ScrollRect(滚动视图)是Unity UGUI中的一个常用组件,用于在UI界面中 ...

  8. IOS 16 无法打开开发版或者企业版本APP解决方案 - 需要开启开发者模式

    在IOS 16系统上,打开开发版本APP,或者企业版本APP时,会看到如下的提示信息: 需要开启开发者模式, xxx 需要在开发者模式下运行. 启用开发者模式前, 此App不可用 这个时由于IOS 1 ...

  9. Skynet通讯遇到的奇怪问题

    问题 最近在做一个内部通讯的服务器, 用的自带的gateserver和socketchannel做通讯, 在使用skynet.unpack或者string.unpack("XXXX" ...

  10. Solution -「CF 1073G」Yet Another LCP Problem

    Description Link. 给定字符串,正整数集合 \(A,B\),满足 \(\forall u\in A,v\in B,1\le u,v\le n\). 求 \(\sum_{i\in A}\ ...