POJ NO.2718 Smallest Difference(DFS)

12 篇文章 0 订阅

问题描述:

给你一些整数(0,1,2,......,9)且个数大于等于2小于等于10,它们互相组合算绝对值,让你求出最小的绝对值!

注意:

1.   0---9这些数每个最多出现一次

2.   不存在前导0的情况

题目链接:点击打开链接

思路:

假设长度为n那么只有两个数长度相等(或者长度差为1)时最小,我们就可以枚举出n/2个元素,再把剩下的组合找出来作差比较即可。

代码:

#include<iostream>
#include<cstdio>
#include<cmath>
#include<queue>
#include<cstring>
#include<algorithm>
#define INF 0x3f3f3f3f

using namespace std;

int a[20], b[20], res, n;
bool booll[20];

void solve(int first){
    int second = 0, k = 0;
    for(int i = 0; i < n; i++)
        if(!booll[i]){
            b[k++] = a[i];
            second = second*10 + a[i];
        }
    if(b[0] != 0 || k == 1)
        res = min(res, abs(first - second));
    while(next_permutation(b, b + k)){
            second = 0;
        for(int i = 0; i < k; i++)
            second = second*10 + b[i];
        if(b[0] != 0 || k == 1)
            res = min(res, abs(first - second));
    }
}

void DFS(int j, int first){
    if(j == (n / 2)){//要想差的绝对值最小个数需要均分
        solve(first);
        return;
    }
    //枚举
    for(int i = 0; i < n; i++){
        if(!booll[i]){
            if(j == 0 && n > 3 && a[i] == 0)
                continue;
            booll[i] = true;
            DFS(j + 1, first*10 + a[i]);
            booll[i] = false;
        }
    }
}

int main(){
    int t;
    scanf("%d", &t);
    getchar();
    while(t--){
        n = 0;
        char ch;
        //借鉴某大牛的读取方式,很巧妙,学习了
        while((ch = getchar()) != '\n'){
            if(ch == ' ') continue;
            a[n++] = ch - '0';
        }
        //当元素为10的时候答案只有一种,直接剥离出来
        if(n == 10){
            cout << "247" << endl;
            continue;
        }
        res = INF;
        memset(booll, false, sizeof(booll));
        DFS(0, 0);
        printf("%d\n", res);
    }
    return 0;
}


评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值