c语言题目排列式

链接:https://ac.nowcoder.com/acm/contest/18839/1002
来源:牛客网

题目描述


  7254是一个不寻常的数,因为它可以表示为7254 = 39 x 186,这个式子中1~9每个数字正好出现一次
  输出所有这样的不同的式子(乘数交换被认为是相同的式子)
  结果小的先输出;结果相同的,较小的乘数较小的先输出。

输入描述:

  每一行输出一个式子,式子中的等号前后空格、乘号(用字母x代表)前后空格
  较小的乘数写在前面

输出描述:

 

下面是我对于此题的理解

  从此题的实例输出上来看,数的分布都是在1000-9999之间的,但由于题目的要求,范围可以继续缩小至1234-9876之间。那我们可以从1234开始,看它会被哪两个数整除。从1开始,1234/1=1234,这时候我们得到了3个数字,分别是1234,1,1234这三个数。我们再创建一个数组sum[10],将里面的数都设为0,对这三个数进行一个拆分,1234拆成1 2 3 4,1拆成1,1234拆成1 2 3 4,分别对应着1 2 3 4这几个数字,那对应的数组里面的内容就要对应的相加,最后再统计1 2 3 4 5 6 7 8 9是否都出现过一次即可。

不过要注意一个点,就是一个式子它可能有两种表示方式,例如7254 = 39 x 186还可以用7254 = 186 x 39来表示,因此对于除数的范围也要有限制,限制到其根号位即可,sqrt(7254)就是除数的最大值了

这是我的代码

#include<stdio.h>
#include<math.h>

int panduan(int i, int j, int k)
{
  int sum[10] = { 0 };
  int a = 1, n;
  while (i > 0)//对数的拆分
  {
    n = i % 10;
    sum[n]++;//对应数组数字
    i /= 10;
    if (sum[n] == 2)//1-9其中如果有一个数字达到2个了就不符合题目需求了
    return 0;
  }
  while (j > 0)//同上
  {
    n = j % 10;
    sum[n]++;
    j /= 10;
    if (sum[n] == 2)
    return 0;
  }
  while (k > 0)
  {
    n = k % 10;
    sum[n]++;
    k /= 10;
    if (sum[n] == 2)
    return 0;
  }
  for (n = 1; n < 10; n++)//最后再判断一次1-9是否都只出现过一次
  {
    if (sum[n] != 1)
    return 0;
  }
  return a;
}
int main()
{
  int i, j, k;
  for (i = 1234; i <= 9876; i++)//对数的查找,遍历手段
  {
    for (j = 1; j <= sqrt(i); j++)//对于除数的限制
    {
      k = i / j;
      if (k * j == i)
    {
    if (panduan(i, j, k))//判断i,j,k三个数的数字是否刚好1-9各一个
    {
      printf("%d = %d x %d\n", i, j, k);//输出
    }
  }
return 0;
}

 

 

 

 


posted @ 2022-09-16 16:51  彼岸的约定  阅读(399)  评论(0编辑  收藏  举报