带分数(dfs,next_permutation)

问题描述

100 可以表示为带分数的形式:100 = 3 + 69258 / 714。

还可以表示为:100 = 82 + 3546 / 197。

注意特征:带分数中,数字1~9分别出现且只出现一次(不包含0)。

类似这样的带分数,100 有 11 种表示法。

输入格式

从标准输入读入一个正整数N (N<1000*1000)

输出格式

程序输出该数字用数码1~9不重复不遗漏地组成带分数表示的全部种数。

注意:不要求输出每个表示,只统计有多少表示法!

样例输入1

100

样例输出1

11

样例输入2

105

样例输出2

6

解法一:直接用c++里面求全排列的函数next_permutation,这样比较好理解,但用时比较长

#include<iostream>
#include <algorithm>
using namespace std;

int sum(int start,int end,int a[])
{
    int i,sum=0;
    for(i=start; i<end; i++)
        sum=sum*10+a[i];
    return sum;
}

int main()
{
    int m,aws=0,a[10];
    int i,j;

    scanf("%d",&m);
    for(i=0; i<9; i++)
        a[i]=i+1;
    do
    {
        for(i=1; i<10; i++)
        {
            int m1=sum(0,i,a);
            if(m1>=m)
                continue;      //不满足条件直接跳过
            for(j=i+(10-i)/2; j<9; j++)      //从第一个数用过的数后开始
            {
                int m2=sum(i,j,a);
                int m3=sum(j,9,a);
                if(m2%m3==0&&m==m1+m2/m3)
                {
                    aws++;  //  统计符合条件的
                }
            }
        }
    }
    while(next_permutation(a, a+9));  //枚举全排列
    printf("%d",aws);
    return 0;
}

  其中next_permutation函数部分可以用dfs代替,代码如下:(关于用dfs实现全排列的思想请见链接:)

#include<cstdio>
#include <algorithm>
#include <cmath>
using namespace std;
int flag[11]={0};
int a[11];
int ncount=0;
int pp=0;
int getSum(int start,int end,int a[])
{
	int sum=0;
	for(int i=start;i<end;i++)
	{
		sum=sum*10+a[i];
	}
	return sum;
}
void Found(int a[],int n)
{
	int re1,re2,re3;
	re1=0;
	re2=0;
	re3=0;
	for(int i=1;i<10;i++)
		{
			re1=getSum(0,i,a);
			if(re1>=n) continue;
			for(int j=i+(10-i)/2;j<9;j++)
			{
				re2=getSum(i,j,a);
				re3=getSum(j,9,a);
				if(re2>re3&&re2%re3==0&&n==re1+re2/re3)
				{
					ncount++;
				}
			}
		  }
}
void DFS(int start,int m)//对1~9进行全排列
{
    int i;
    if(start==9)
        Found(a,m);  //上面的do循环
    else
    {
        for(i=1; i<10; i++)
        {
			if(!flag[i])
			{
				 a[start]=i;
				 flag[i]=1;   //标记是否用过
				 DFS(start+1,m);//选择好一位开始选下一位
				 flag[i]=0;
			}
        }
    }
}

int main()
{
	int n;
	scanf("%d",&n);
	int i,j;
	int a[10];

	for(i=0;i<9;i++)
	{
		a[i]=i+1;
	}
	DFS(0,n);
	printf("%d",ncount);
	return 0;
}

  

原文地址:https://www.cnblogs.com/curo0119/p/8413863.html

时间: 2024-11-01 09:31:58

带分数(dfs,next_permutation)的相关文章

蓝桥杯 历届试题 带分数 DFS最容易理解版,内有解析

历届试题 带分数 时间限制:1.0s   内存限制:256.0MB 问题描述 100 可以表示为带分数的形式:100 = 3 + 69258 / 714. 还可以表示为:100 = 82 + 3546 / 197. 注意特征:带分数中,数字1~9分别出现且只出现一次(不包含0). 类似这样的带分数,100 有 11 种表示法. 输入格式 从标准输入读入一个正整数N (N<1000*1000) 输出格式 程序输出该数字用数码1~9不重复不遗漏地组成带分数表示的全部种数. 注意:不要求输出每个表示,

蓝桥杯练习系统历届试题 带分数 dfs

问题描述 100 可以表示为带分数的形式:100 = 3 + 69258 / 714. 还可以表示为:100 = 82 + 3546 / 197. 注意特征:带分数中,数字1~9分别出现且只出现一次(不包含0). 类似这样的带分数,100 有 11 种表示法. 输入格式 从标准输入读入一个正整数N (N<1000*1000) 输出格式 程序输出该数字用数码1~9不重复不遗漏地组成带分数表示的全部种数. 注意:不要求输出每个表示,只统计有多少表示法! 样例输入1 100 样例输出1 11 样例输入

洛谷 P1618 三连击(升级版)【DFS/next_permutation()/技巧性枚举/sprintf】

[链接]:https://www.luogu.org/problemnew/show/P1618 题目描述 将1,2,…,9共9个数分成三组,分别组成三个三位数,且使这三个三位数的比例是A:B:C,试求出所有满足条件的三个三位数,若无解,输出“No!!!”. //感谢黄小U饮品完善题意 输入输出格式 输入格式: 三个数,A B C. 输出格式: 若干行,每行3个数字.按照每行第一个数字升序排列. 输入输出样例 输入样例#1: 复制 1 2 3 输出样例#1: 复制 192 384 576 219

蓝桥杯 - 带分数 (DFS)

历届试题 带分数 时间限制:1.0s   内存限制:256.0MB 问题描述 100 可以表示为带分数的形式:100 = 3 + 69258 / 714. 还可以表示为:100 = 82 + 3546 / 197. 注意特征:带分数中,数字1~9分别出现且只出现一次(不包含0). 类似这样的带分数,100 有 11 种表示法. 输入格式 从标准输入读入一个正整数N (N<1000*1000) 输出格式 程序输出该数字用数码1~9不重复不遗漏地组成带分数表示的全部种数. 注意:不要求输出每个表示,

HDU1027 Ignatius and the Princess II 【next_permutation】【DFS】

Ignatius and the Princess II Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 4571    Accepted Submission(s): 2733 Problem Description Now our hero finds the door to the BEelzebub feng5166. He o

HDU 1027 Ignatius and the Princess II[DFS/全排列函数next_permutation]

Ignatius and the Princess II Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 9458    Accepted Submission(s): 5532 Problem Description Now our hero finds the door to the BEelzebub feng5166. He op

蓝桥杯 历届试题 带分数

历届试题 带分数 时间限制:1.0s 内存限制:256.0MB 问题描述 100 可以表示为带分数的形式:100 = 3 + 69258 / 714. 还可以表示为:100 = 82 + 3546 / 197. 注意特征:带分数中,数字1~9分别出现且只出现一次(不包含0). 类似这样的带分数,100 有 11 种表示法. 输入格式 从标准输入读入一个正整数N (N<1000*1000) 输出格式 程序输出该数字用数码1~9不重复不遗漏地组成带分数表示的全部种数. 注意:不要求输出每个表示,只统

(DFS、全排列)POJ-2718 Smallest Difference

题目地址 简要题意: 给若干组数字,每组数据是递增的在0--9之间的数,且每组数的个数不确定.对于每组数,输出由这些数组成的两个数的差的绝对值最小是多少(每个数出现且只出现一次). 思路分析: 对于n个数,必定为分成两个位数分别为n/2和n-n/2的数时才可能取得差的绝对值最小.两组数分别进行全排列比较大小,这样比较次数最大为(10A5)*(5A5)=10!,在可以接受的范围内. 参考代码: 1 #include<stdio.h> 2 #include<cstring> 3 #in

[HDU 1427]速算24点(DFS暴搜)

题目连接:  http://acm.hdu.edu.cn/showproblem.php?pid=1427 思路:简单的DFS,dfs(sum,next,p)表示当前已经算出的值是sum,括号中算出的值是next,当前使用的卡片下标为p,实际上是把括号外和括号内的两部分值分成sum和next来处理了. 直觉告诉我们4个数只需要一层括号参与运算就够了,不会也不必用多重括号改变运算顺序,因此上面的dfs思路是正确的. 那么对于下一张卡片,有两种处理方式: 1.把next算入sum中,下一张卡片成