POJ 2718

问题描述:

给一串数,求划分后一个子集以某种排列构成一个数,余下数以某种排列构成另一个数,求这两个数最小的差,注意0开头的处理。

超时问题:一开始是得到一个数列的组合之后再从中间进行切割得到两数,会超时。后来采用的方法是将前面的数在DFS中得到固定,在函数work中对后面(n-n/2)个数进行排列组合。

针对整个数列的dfs排列组合剪枝,若当前搜索的第二个数后面全部补零与第一个数所产生的差值比当前所搜索到的结果还要大,那么就直接返回。这个剪枝就是超时与几十MS的差距
int nums[10]={1,10,100,1000,10000,100000,1000000};

解法一:朴素permutation

#include <iostream>
#include <algorithm>
#include <map>
#include <string>
#include <string.h>
#include <ctype.h>
#include <vector>
#include <math.h>
using namespace std; char s[1000];
int t;
int main()
{
cin>>t;
getchar();
while(t--)
{
int a[11],num=0,ans=0x7f7f7f;
gets(s);
for(int i=0;i<strlen(s);i++)
if (s[i] >= '0'&&s[i] <= '9')//删除空格
a[num++]=s[i]-'0';
sort(a,a+num);
do
{
int num1=0,num2=0;
//前面那个数的首位不能是0,后面那个数的首位也不能是0,还有当为输入是10时,要么前面那个数的是0,要么后面的那个数是0,所以条件num>2加"||"前后都一样
if(!a[0]||(!a[num/2] && num>2))continue;
for(int i=0;i<num/2;i++)num1=num1*10+a[i];
for(int i=num/2;i<num;i++)num2=num2*10+a[i];
ans=min(ans,abs(num1-num2));
}while(next_permutation(a, a+num));
cout<<ans<<endl;
}
return 0;
}

解法二:dfs+permutation

#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>//next_permutation包含其中
using namespace std; int a[15], vis[15], n, ans, aa, bb; void solve(int aa) {
int len = 0, flag = 1, b[15];
bb = 0;
for(int i = 0; i < n; i++)
if(!vis[i]) b[len++] = a[i];
for(int i = 0; i < len; i++) {
if(i == 0 && b[i] == 0) flag = 0;
bb = bb * 10 + b[i];
}
if(flag) ans = min(ans, abs(aa-bb));
while(next_permutation(b, b+len)) {
bb = 0;
flag = 1;
for(int i = 0; i < len; i++) {
if(i == 0 && b[i] == 0) flag = 0;
bb = bb * 10 + b[i];
}
if(flag) ans = min(ans, abs(aa-bb));
}
return;
} void dfs(int k, int res) {
if(k == n/2) {
solve(res);
return;
}
for(int i = 0; i < n; i++) {
if(!vis[i]) {
if(a[i] == 0 && k == 0) continue;
vis[i] = 1;
dfs(k+1, res*10+a[i]);
vis[i] = 0;
}
}
return;
} int main() {
int kase;
scanf("%d", &kase);
getchar();
while(kase--) {
n = 0;
char ch;
memset(a, 0, sizeof(a));
memset(vis, 0, sizeof(vis));
while((ch = getchar()) != '\n') {
if(ch == ' ')
continue;
else a[n++] = ch - '0';
}
if(n == 2 && a[0] == 0) { //当只有两个数字,且其中一个为0时,特殊处理
printf("%d\n", a[1]-a[0]);
continue;
}
ans = 1 << 30;
dfs(0, 0);
printf("%d\n", ans);
}
return 0;
}

POJ 2718【permutation】的更多相关文章

  1. POJ 3187【permutation】

    POJ 3187 给定N值,从而确定了数据的范围及长度,暴力枚举数列,接下来类似杨辉三角的递推计算.注permutation从递增有序数列开始枚举,枚举到符合sum值时退出即可 #include &l ...

  2. 【简●解】POJ 1845 【Sumdiv】

    POJ 1845 [Sumdiv] [题目大意] 给定\(A\)和\(B\),求\(A^B\)的所有约数之和,对\(9901\)取模. (对于全部数据,\(0<= A <= B <= ...

  3. POJ 2154 【POLYA】【欧拉】

    前记: TM终于决定以后干啥了.这几天睡的有点多.困饿交加之间喝了好多水.可能是灌脑了. 切记两件事: 1.安心当单身狗 2.顺心码代码 题意: 给你N种颜色的珠子,串一串长度问N的项链,要求旋转之后 ...

  4. POJ 3230 【DP】

    题意: 某货旅行,在n个城市呆m天. 给出从第i个城市到第j个城市的路费,或者留在某个城市的生活费. 给出在第i天在第j个城市的收益. 可以在城市之间任意穿梭逗留没有其他特殊要求. 求收益最大是多少. ...

  5. Tiling POJ 2506 【大数】

    id=2506">http://poj.org/problem?id=2506 Description In how many ways can you tile a 2xn rect ...

  6. poj 2431 【优先队列】

    poj 2431 Description A group of cows grabbed a truck and ventured on an expedition deep into the jun ...

  7. poj 2385【动态规划】

    poj 2385 Apple Catching Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 14007   Accepte ...

  8. POJ 1286 【POLYA】

    题意: 给你三种颜色的珠子,每次给你N,问在旋转,翻转之后视作相同的情况下,能组成多少种不同的项链. 思路: 让我们借这道题拯救一下我对POLYA定理的理解... sigma(m^(gcd(i,n)) ...

  9. POJ 3270 【组合数学】

    题意: 给长度为N的学列,然后让你通过置换来使其递增.原序列没有相同的数字. 1 ≤ N ≤ 10,000 ai<=100000 思路: 先找到循环,然后根据贪心只有两种比较好的情况,让循环里边 ...

随机推荐

  1. 08-DML(插入、更新、删除)

    1. 插入 (1). 插入完整数据记录 (2). 插入数据记录的一部分 (3). 插入多条记录(MySQL特有的) INSERT INTO table_name (column1,column2,co ...

  2. hadoop - 基础操作

    查看文件: [root@hadoop hadoop]# hadoop fs -lsr /drwxr-xr-x - root supergroup 0 2016-12-27 10:49 /homedrw ...

  3. uboot 如何向内核传递参数

    a.uboot 向内核传递的参数有两种类型 1.一个是bootargs 2.一个是环境参数, 而环境参数的设置靠的是 Y:\junda\JdLinuxApp\A1801_uboot\source\u- ...

  4. sizeof strlen区别于联系

    http://www.cnblogs.com/carekee/articles/1630789.html

  5. mysql 原理 ~ change buffer

    一 简介:今天咱们来聊聊mysql的change buffer二 详细说明   1 +-change Buffer和数据页一样,也是物理页的一个组成部分,数据结构也是一颗B+树,这棵B+树放在共享表空 ...

  6. Ajax跨域访问解决方案

    No 'Access-Control-Allow-Origin' header is present on the requested resource. 当使用ajax访问远程服务器时,请求失败,浏 ...

  7. SpringBoot整合Jdbc

    (1).添加相关依赖 <dependency> <groupId>org.springframework.boot</groupId> <artifactId ...

  8. Spring使用RMI进行远程方法调用

    (1).我新建了三个项目,SpringRmiApi(存放提供者和消费者共有的xx,例如实体类以及服务接口等等).SpringRmiService(服务提供者).SpringRmiProvider(服务 ...

  9. 【逆向知识】动态调试技巧-C++代码逆向

    1.C++类代码的特点 寄存器ECX传参时一般用作this指针(对象地址)或是计数器. 有ecx传参的call,是成员函数,构造函数,析构函数 能访问成员变量的函数都会有ecx传参 静态函数.全局函数 ...

  10. java项目中oracle配置说明

    配置信息: #oracle database settings jdbc.url::orcl jdbc.username=cognos_data jdbc.password=cognos_data j ...