简单dfs专题

由于被状压DP打自闭,觉着来dfs找找自信,没成想依旧自闭orz

 

HDU 2610 Sequence one

题意:

给出n个数字,让你求出非递减序列,且个数

思路:

dfs(last , now , len ),main函数遍历序列长度len。

dfs思想就是深搜搜到底(当前长度now = len),然后输出,接着回溯查找下一个。这样是满足题目要求的按下标排序,下标小的在前。开个数组s[ ]保存一路过来的结果。 难点在于剪枝,这里有三种剪枝

1) 当找到的序列个数 cnt == p , 结束递归

2)例如 1 2 3 3 4 3 , 我们希望找长度为2的序列,当我们找到第一位上的值 3 即序列为 3 X ,  X的可选值有 3 4 3,那么最后一个3 和第一个3 是一种情况,我们要剪掉 即查找 [last+1 --- j-1] 上有没有和 a[j]相等的 , a[j] 就是最后一个3

3)假如扫了一遍过去,cnt的值没有变化,那么证明这个序列已经不存在更长的非递减子序列了,那么main直接退出

代码:

#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include

using namespace std;

const int maxn = 1001;
typedef long long ll;

int a[maxn],s[maxn];
int n,p,cnt;
void dfs(int last,int now,int len)
{

   if(n-last < len - now) return;
    if(cnt >= p) return;
    if(now == len)
    {
        // 输出
        cnt++;
        printf("%d",s[0]);
        for(int i=1; i0 && a[i] < s[now-1])
            continue;
        int mark = 0;
        for(int j=last+1; j= p)
                break;
        }
        printf("\n");
    }
    return 0;
}

HDU Fling

最近深搜写的乱七八糟,但是都莫名其妙能过hhhhh,这篇完结,接着回去刷状压DP

感觉这个代码写得还阔以

#include 
#include 
#include 
#include 
#include 
#include 

using namespace std;
const int maxn = 10;
const int inf = 0x3f3f3f3f;

char mp[maxn][maxn];

struct Node
{
    int z,x,y;
};

vectorans;

int all;
int flag = 0;

int dir[4][2] = {-1,0,0,-1,0,1,1,0};
void dfs1(int now);

void dfs(int x,int y,int z, int now, int step)
{
    mp[x][y] = 'X';
    int nx = x+dir[z][0], ny = y+dir[z][1];
    while(mp[nx][ny] == 'X' && nx>=1&& nx<=7 && ny>=1 && ny<=8)
    {
        nx = nx + dir[z][0];
        ny = ny + dir[z][1];
    }
    if(mp[nx][ny] == 'O')
    {
        mp[nx-dir[z][0]][ny-dir[z][1]] = 'O';
        dfs(nx,ny,z,now,step+1);
        mp[nx-dir[z][0]][ny-dir[z][1]] = 'X';
        mp[x][y] = 'O';
    }
    else
    {
        if(step == 0)
        {
            mp[x][y] = 'O';
            return;
        }
        dfs1(now+1);
        mp[x][y] = 'O';
    }
}

int check()
{
    int cnt = 0;
    for(int i=1; i<=7; i++)
    {
        for(int j=1; j<=8; j++)
        {
            if(mp[i][j] == 'O')
            {
                cnt++;
                if(cnt == 2)
                    return 0;
            }
        }
    }
    return 1;
}
void dfs1(int now) // 开始拉一下
{
    if(check())
    {
        for(int t=0; t=1&& nx<=7 && ny>=1 && ny<=8)
                    {
                        //ans[now] = make_pair(z,make_pair(i,j));
                        Node p;
                        p.z = z;
                        p.x = i;
                        p.y = j;
                        ans.push_back(p);
                        dfs(i,j,z,now+1,0);
                        ans.pop_back();
                        if(flag == 1)
                            return;
                    }
                }
            }
        }
    }
}

int main()
{   int cas = 1;

    while(scanf("%s",mp[1]+1) != EOF)
    {

        flag = 0;
        for(int i=2; i<=7; i++)
            scanf("%s",mp[i]+1);
        for(int i=1; i<=7; i++)
        {
            for(int j=1; j<=8; j++)
                if(mp[i][j] == 'O')
                {
                    all++;
                }
        }
        if(cas != 1)
            cout<

 

你可能感兴趣的:(算法,dfs,剪枝)