アルゴリズム高度ガイド-検索-深さ優先探索

1.子猫の登山の
質問へのリンク
ここに画像の説明を挿入

#include<iostream>
#include<algorithm>

using namespace std;
const int N=20;
int cat[N],car[N];
int n,m;
int ans=N;

void dfs(int k,int l)
{
    
    
	if(l>=ans) return;

	if(k==n)
	{
    
    
		ans=l;
		return;
	}

	for(int i=0;i<l;i++)
	{
    
    
		if(cat[k]+car[i]<=m)
		{
    
    
			car[i]+=cat[k];
			dfs(k+1,l);
			car[i]-=cat[k];
		}
	}
	car[l]=cat[k];
	dfs(k+1,l+1);
	car[l]=0;



}


int main()
{
    
    
	cin>>n>>m;

	for(int i=0;i<n;i++)
	cin>>cat[i];
	sort(cat,cat+n,greater<int>());

	dfs(0,0);

	cout<<ans<<endl;
	


}

2.数独

トピックリンク
ここに画像の説明を挿入

#include <iostream>
using namespace std;

const int N = 9;

int ones[1 << N], map[1 << N];

int row[N], col[N], cell[5][5];

string str;
inline int lowbit(int x)
{
    
    
    return x & -x;
}

void init()
{
    
    
    for (int i = 0; i < N; i++)
        row[i] = col[i] = (1 << N) - 1; //初始状态每一个数都可以选
    for (int i = 0; i < 3; i++)
        for (int j = 0; j < 3; j++)
            cell[i][j] = (1 << N) - 1;
}

inline int get(int x, int y)
{
    
    
    return row[x] & col[y] & cell[x / 3][y / 3]; //求交集
}

bool dfs(int cnt)
{
    
    
    if (!cnt)
        return true;
    int minv = 10;
    int x, y;
    for (int i = 0; i < N; i++)
        for (int j = 0; j < N; j++)
            if (str[i * 9 + j] == '.')
            {
    
    
                int t = ones[get(i, j)];
                if (t < minv)
                {
    
    
                    minv = t;
                    x = i, y = j;
                }
            }

    for (int i = get(x, y); i; i -= lowbit(i))
    {
    
    
        int t = map[lowbit(i)];

        // 修改状态
        row[x] -= 1 << t;
        col[y] -= 1 << t;
        cell[x / 3][y / 3] -= 1 << t;
        str[x * 9 + y] = '1' + t;

        if (dfs(cnt - 1))
            return true;

        // 恢复现场
        row[x] += 1 << t;
        col[y] += 1 << t;
        cell[x / 3][y / 3] += 1 << t;
        str[x * 9 + y] = '.';
    }

    return false;
}



int main()
{
    
    
    for (int i = 0; i < N; i++)
        map[1 << i] = i;
    for (int i = 0; i < 1 << N; i++) //计算一个二进制数包含多少个1
    {
    
    
        int s = 0;
        for (int j = i; j > 0; j -= lowbit(j))
            s++;

        ones[i] = s;
    }

    while (cin >> str, str[0] != 'e')
    {
    
    
        init();
        int cnt = 0; //需要填的个数
        for (int i = 0, k = 0; i < N; i++)
            for (int j = 0; j < N; j++, k++)
            {
    
    
                if (str[k] != '.')
                {
    
    
                    int t = str[k] - '1'; //1~9变成0~8
                    row[i] -= 1 << t;
                    col[j] -= 1 << t;
                    cell[i / 3][j / 3] -= 1 << t;
                }
                else
                    cnt++;
            }
        dfs(cnt);
        cout << str << endl;
    }
}

おすすめ

転載: blog.csdn.net/jahup/article/details/112060069