C++深度优先搜素

深度优先搜索特点:穷举所有情况、全排列==完全图、顶点数最好小于11、需要哈希表和栈的数据结构基础。

算法描述,第一步,初始化数据结构,全排列在计算过程中,需要利用一个哈希表visited和一个栈stack来记录当前访问过的节点。其中哈希表是为了快速查找某个节点是否被访问,并且执行插入,栈是为了记录顶点的访问顺序。

第二步,顶点访问,依次访问所有顶点,如果发现这个顶点没有在哈希表中,则把它插入哈希表,并且把这个顶点入栈。这样一来,哈希表和栈中,存储的就是本次遍历中存储的点。

第三步,递归调用,利用递归进行调用自身,继续访问下一个节点。

第四步,当本次访问的顶点数等于总顶点数的时候,栈中的元素就代表一个排列,把排列进行输出或者做其他相应的处理。

第五步,回溯,当没有任何顶点需要访问的时候,进行回溯。回溯就是将栈顶元素出栈,并且将这个元素从哈希表中移除

代码分析,

第一步,初始化数据结构

function initData(visited, stack)

visited.clear()

stack.clear()

第二步,框架代码

function dfs(depth, maxDepth)

if depth == maxDepth

print(stack)

return

for i -> (0, maxDepth - 1)

if i not in visited

visited.add(i)

stack.push(i)

dfs(depth+1, maxDepth)

visited.remove(i)

stack.pop()

这个算法时间复杂度为n的阶乘

代码练习 1 对应蓝桥云课 排列序数 代码见下

cpp 复制代码
#include <iostream>
#include <string>
#include <algorithm>
#include <cstring>
using namespace std;

#define maxn 10
string str;

int ans;
int visited[maxn];
int stack[maxn];
int cnt;
string sorted;
void dfs(int depth, int maxDepth){
  if(depth == maxDepth){
    int i;
    for(i=0; i<maxDepth; ++i){
      int idx = stack[i];
      if(sorted[idx] != str[i]){
        break;
      }
    }
    if(i == maxDepth){
      ans = cnt;
    }
    ++cnt;
    return;
  }
  for(int i=0; i<maxDepth; ++i){
    if(!visited[i]){
      visited[i] = 1;
      stack[depth] = i;
      dfs(depth+1, maxDepth);
      visited[i] = 0;
    }
  }
}
int main()
{
  cin >> str;
  sorted = str;
  sort(sorted.begin(), sorted.end());
  memset(visited, 0, sizeof(visited));
  cnt = 0;
  dfs(0, str.size());
  cout << ans << endl;
  // 请在此输入您的代码
  return 0;
}

代码练习 2 对应蓝桥云课 十位数宝藏代码 代码见下

cpp 复制代码
#include <iostream>
using namespace std;

#define maxn 10

int visited[maxn];
int stack[maxn];

long long Min = (long long)9876543210;
long long Max = 0;

void dfs(int depth, int maxDepth, long long ans){
  if(depth == maxDepth){
    if(ans % 11 == 0){
      if(ans < Min) Min = ans;
      if(ans > Max) Max = ans;
    }
    return;
  }
  if(depth == 1){
    if(ans == 0){
      return;
    }
  }
  for(int i=0; i<maxDepth; ++i){
    if(!visited[i]){
      visited[i] = 1;
      stack[depth] = i;
      dfs(depth+1, maxDepth, ans*10 + i);
      visited[i] = 0;
    }
  }
}

int main()
{
  dfs(0, 10, 0);
  cout << Max - Min << endl;

  // 请在此输入您的代码
  return 0;
}

代码练习3 对应蓝桥云课带分数, 代码见下

cpp 复制代码
#include <iostream>
using namespace std;

// #define maxn 10

// int visited[maxn];
// int stack[maxn];

// void dfs(int depth, int maxDepth){
//   if(depth == maxDepth){
//      // stack存储了[0, maxDepth-1]的全排列
//     return;
//   }
//   for(int i=0; i<maxDepth; ++i){
//     if(!visited[i]){
//       visited[i] = 1;
//       stack[depth] = i;
//       dfs(depth+1, maxDepth);
//       visited[i] = 0;
//     }
//   }
// }

#define maxn 10
int N;
int ans;
int visited[maxn];

int pow10[maxn] = {
  1,
  10,
  100,
  1000,
  10000,
  100000,
  1000000,
  10000000,
  100000000,
  1000000000
};
int cnt(int sum){
  int ans = 0;
  for(int i = 8; i >= 0; --i){
    int x = sum / pow10[i];
    if(N <= x){
      break;
    }
    int y = N - x;
    int z = sum % pow10[i];
    for(int j = 1 ; ; ++j){
      int fm = z % pow10[j];
      int fz = z / pow10[j];
      if(fz < fm){
        break;
      }
      if(fz % fm == 0){
        if(fz / fm == y){
          ++ans;
        }
      }
    }
  }
  return ans;
}

void dfs(int depth, int maxDepth, int sum){
  if(depth == maxDepth){
    ans += cnt(sum);
     // stack存储了[0, maxDepth-1]的全排列
    return;
  }
  for(int i=0; i<maxDepth; ++i){
    if(!visited[i]){
      visited[i] = 1;
      dfs(depth+1, maxDepth, sum*10+(i+1));
      visited[i] = 0;
    }
  }
}

int main()
{
  cin >> N;
  dfs(0, 9, 0);
  cout << ans << endl;

  // 请在此输入您的代码
  return 0;
}
相关推荐
沐怡旸2 小时前
【底层机制】std::string 解决的痛点?是什么?怎么实现的?怎么正确用?
c++·面试
River4165 小时前
Javer 学 c++(十三):引用篇
c++·后端
感哥7 小时前
C++ std::set
c++
侃侃_天下8 小时前
最终的信号类
开发语言·c++·算法
博笙困了8 小时前
AcWing学习——差分
c++·算法
echoarts8 小时前
Rayon Rust中的数据并行库入门教程
开发语言·其他·算法·rust
Aomnitrix8 小时前
知识管理新范式——cpolar+Wiki.js打造企业级分布式知识库
开发语言·javascript·分布式
青草地溪水旁9 小时前
设计模式(C++)详解—抽象工厂模式 (Abstract Factory)(2)
c++·设计模式·抽象工厂模式
青草地溪水旁9 小时前
设计模式(C++)详解—抽象工厂模式 (Abstract Factory)(1)
c++·设计模式·抽象工厂模式
感哥9 小时前
C++ std::vector
c++