zoukankan      html  css  js  c++  java
  • 机试笔记--搜索

    一.枚举

    例题一 百鸡问题

    #include<bits/stdc++.h>
    using namespace std;
    
    int main(){
        int n;
        while (cin>>n) {
            for (int i = 0; i <= 100; i++) {
                for (int j = 0; j <= 100 - i; j++) {
                    int m = 100 - i - j;
                    if (i * 5 + 3 * j + (double) 1 / 3 * m > n)
                        break;
                    else
                        cout << "x=" << i << ",y=" << j << ",z=" << m << endl;
    
                }
            }
        }
        return 0;
    }

     例题二 老比尔 

    N  _XYZ_,N是火鸡的数量,现在不知道价格的第五位和第一位,求一只火鸡的价格

    有多个满足条件的价格时选择价格最高的。

    假设一只火鸡的价格为整数,总价为5位数

    #include <bits/stdc++.h>
    using namespace std;
    
    int main(void){
        int n, a, b, c, d, e, bcd, abcde;
        while(cin >>n >>a >>b >>c){
            bool flag = false;
            bcd = a*1000 + b*100 +c*10;
            for(int a=9; a>=1; a--){//倒着搜索,保证是最大值
                for(int e=9; e>=0; e--){
                    abcde = a*10000 + bcd + e;
                    if(abcde%n==0){
                        flag = true;
                        printf("%d %d %d
    ", a, e, abcde/n);
                        break;
                    }
                }
                if(abcde%n==0) break;
            }
            if(!flag) cout <<0 <<endl; //未找到返回0
        }
        return 0;
    }

     广度优先搜索

    例题:玛雅人的密码

    玛雅人有一种密码,如果字符串中出现连续的2012四个数字就能解开密码。给一个长度为N的字符串,(2=<N<=13)该字符串中只含有0,1,2三种数字,问这个字符串要移位几次才能解开密码,每次只能移动相邻的两个数字。例如02120经过一次移位,可以得到20120,01220,02210,02102,其中20120符合要求,因此输出为1.如果无论移位多少次都解不开密码,输出-1。

    输入:输入包含多组测试数据,每组测试数据由两行组成。

    第一行为一个整数N,代表字符串的长度(2<=N<=13)。

    第二行为一个仅由0、1、2组成的,长度为N的字符串。

    输出:输出最少的移位次数,没有,输出-1

    分析

    • 将所有可能的字符串列举出来,然后判断是否有包含“2012”的
    • 又要求输出最少的移位次数,所以应该以图的形式列举出来,然后按照广度优先搜索的方式进行遍历(因为要求的是最少的移位次数)
    • 建立这张图的方式:将源字符串作为第一个节点, 然后将它的移位字符串作为邻接点即可.
    #include <bits/stdc++.h>
    using namespace std;
    string init;
    int N;
    typedef struct Node
    {
        string s;
        int step;
    }Node;
    
    int bfs()
    {
        Node start;
        start.s=init,start.step=0;
        queue<Node> q;
        q.push(start);
        map<string,int> m;
        m[init]=1;
        while(!q.empty()){
          Node temp=q.front();
          q.pop();
          if(temp.s.find("2012")!=temp.s.npos) return temp.step;
            for(int i=0;i<N-1;i++){
              string now = temp.s;
              char a;
              a=now[i];
              now[i]=now[i+1];
              now[i+1]=a;
              Node node;
              node.s=now,node.step=temp.step+1;
              if(m[now]==0){
                q.push(node);
                m[now]=1;
              }
            }
        }
        return -1;
    }
    int main()
    {
        while(cin>>N>>init){
          cout << bfs() <<endl;
        }
        return 0;
    }

     广度优先搜索的要点:

    1.需要有一个一维或二维数组,或者是哈希表来记录是否访问过某节点

    2.在while(!q.empty())中如果找到,那么就返回,一般是返回搜索的次数

    3.在将周围的节点进队时要判断这个节点是否访问,未访问的话进队并且将这个节点标记

  • 相关阅读:
    百度网盘提速方法
    2020年北京某企Java校招真题
    scrapy中选择器的用法
    scrapy框架基础篇
    selenium模拟浏览器爬取淘宝产品信息
    python连接MongoDB
    pyquery库
    BeautifulSoup4库
    Locust
    【Java】类赋值的使用方式
  • 原文地址:https://www.cnblogs.com/Sunqingyi/p/12713016.html
Copyright © 2011-2022 走看看