如果n的素数分解中的位数(包括幂)与n中的位数相同,则将数字n称为Equidigital。
例如16是一个等值数字,因为其素数分解为2 ^ 4,并且其素数分解具有总计两位数(2和4),与16中的位数总数相同。
再举一个例子,128不是等值数字,因为其素数分解为2 ^ 7,并且总共有2位数字(2和7),而number有3位数字。
所有素数均为Equidigital。
给定数字n,任务是打印所有等于n的Equidigital数字。
例子:
Input: n = 10
Output: 1, 2, 3, 5, 7, 10.
Note that 4, 6, 8 and 9 are not Equidigital.
Input : n = 20
Output : 1 2 3 5 7 10 11 13 14 15 16 17 19
方法(打印所有小于或等于n的Equidigital数字)
- 使用Sundaram筛网计算所有质数,直至10 ^ 6。
- 在n中查找位数。
- 找到n的所有素数,并对每个素数p进行跟随。
- 在p中查找位数。
- 计算除以n的p的最高幂。
- 查找以上两个的总和。
- 比较两个总和。如果两个总和相同,则返回true。
以下是上述想法的实现。
C++
// C++ Program to find Equidigital Numbers till n
#include
using namespace std;
const int MAX = 10000;
// Array to store all prime less than and equal to MAX.
vector primes;
// Utility function for sieve of sundaram
void sieveSundaram()
{
// In general Sieve of Sundaram, produces primes smaller
// than (2*x + 2) for a number given number x. Since
// we want primes smaller than MAX, we reduce MAX to half
// This array is used to separate numbers of the form
// i+j+2ij from others where 1 <= i <= j
bool marked[MAX/2 + 1] = {0};
// Main logic of Sundaram. Mark all numbers which
// do not generate prime number by doing 2*i+1
for (int i=1; i<=(sqrt(MAX)-1)/2; i++)
for (int j=(i*(i+1))<<1; j<=MAX/2; j=j+2*i+1)
marked[j] = true;
// Since 2 is a prime number
primes.push_back(2);
// Print other primes. Remaining primes are of the
// form 2*i + 1 such that marked[i] is false.
for (int i=1; i<=MAX/2; i++)
if (marked[i] == false)
primes.push_back(2*i + 1);
}
// Returns true if n is a Equidigital number, else
// false.
bool isEquidigital(int n)
{
if (n == 1)
return true;
// Count digits in original number
int original_no = n;
int sumDigits = 0;
while (original_no > 0)
{
sumDigits++;
original_no = original_no/10;
}
// Count all digits in prime factors of n
// pDigit is going to hold this value.
int pDigit = 0 , count_exp = 0, p;
for (int i = 0; primes[i] <= n/2; i++)
{
// Count powers of p in n
while (n % primes[i] == 0)
{
// If primes[i] is a prime factor,
p = primes[i];
n = n/p;
// Count the power of prime factors
count_exp++;
}
// Add its digits to pDigit.
while (p > 0)
{
pDigit++;
p = p / 10;
}
// Add digits of power of prime factors to pDigit.
while (count_exp > 1)
{
pDigit++;
count_exp = count_exp / 10;
}
}
// If n!=1 then one prime factor still to be
// summed up;
if (n != 1)
{
while (n > 0)
{
pDigit++;
n = n/10;
}
}
// If digits in prime factors and
// digits in original number are same, then
// return true. Else return false.
return (pDigit == sumDigits);
}
// Driver code
int main()
{
// Finding all prime numbers before limit. These
// numbers are used to find prime factors.
sieveSundaram();
cout << "Printing first few Equidigital Numbers"
" using isEquidigital()\n";
for (int i=1; i<20; i++)
if (isEquidigital(i))
cout << i << " ";
return 0;
}
Java
// Java program to find Equidigital Numbers till n
import java.util.Vector;
import static java.lang.Math.sqrt;
class GFG
{
static final int MAX = 10000;
static Vector primes = new Vector(MAX+1);
// Utility function for sieve of sundaram
static void sieveSundaram()
{
// In general Sieve of Sundaram, produces primes smaller
// than (2*x + 2) for a number given number x. Since
// we want primes smaller than MAX, we reduce MAX to half
// This array is used to separate numbers of the form
// i+j+2ij from others where 1 <= i <= j
boolean marked[] = new boolean[MAX/2 + 1];
// Main logic of Sundaram. Mark all numbers which
// do not generate prime number by doing 2*i+1
for (int i=1; i<=(sqrt(MAX)-1)/2; i++)
for (int j=(i*(i+1))<<1; j<=MAX/2; j=j+2*i+1)
marked[j] = true;
// Since 2 is a prime number
primes.add(2);
// Print other primes. Remaining primes are of the
// form 2*i + 1 such that marked[i] is false.
for (int i=1; i<=MAX/2; i++)
if (marked[i] == false)
primes.add(2*i + 1);
}
// Returns true if n is a Equidigital number, else
// false.
static boolean isEquidigital(int n)
{
if (n == 1)
return true;
// Count digits in original number
int original_no = n;
int sumDigits = 0;
while (original_no > 0)
{
sumDigits++;
original_no = original_no/10;
}
// Count all digits in prime factors of n
// pDigit is going to hold this value.
int pDigit = 0 , count_exp = 0, p = 0;
for (int i = 0; primes.elementAt(i) <= n/2; i++)
{
// Count powers of p in n
while (n % primes.elementAt(i) == 0)
{
// If primes[i] is a prime factor,
p = primes.elementAt(i);
n = n/p;
// Count the power of prime factors
count_exp++;
}
// Add its digits to pDigit.
while (p > 0)
{
pDigit++;
p = p / 10;
}
// Add digits of power of prime factors to pDigit.
while (count_exp > 1)
{
pDigit++;
count_exp = count_exp / 10;
}
}
// If n!=1 then one prime factor still to be
// summed up;
if (n != 1)
{
while (n > 0)
{
pDigit++;
n = n/10;
}
}
// If digits in prime factors and
// digits in original number are same, then
// return true. Else return false.
return (pDigit == sumDigits);
}
// Driver method
public static void main (String[] args)
{
// Finding all prime numbers before limit. These
// numbers are used to find prime factors.
sieveSundaram();
System.out.println("Printing first few Equidigital Numbers" +
" using isEquidigital()");
for (int i=1; i<20; i++)
if (isEquidigital(i))
System.out.print(i + " ");
}
}
Python3
# Python3 Program to find Equidigital
# Numbers till n
import math
MAX = 10000;
# Array to store all prime less
# than and equal to MAX.
primes = [];
# Utility function for sieve of sundaram
def sieveSundaram():
# In general Sieve of Sundaram, produces
# primes smaller than (2*x + 2) for a number
# given number x. Since we want primes smaller
# than MAX, we reduce MAX to half. This array
# is used to separate numbers of the form
# i+j+2ij from others where 1 <= i <= j
marked = [False] * int(MAX / 2 + 1);
# Main logic of Sundaram. Mark all numbers which
# do not generate prime number by doing 2*i+1
for i in range(1, int((math.sqrt(MAX) - 1) / 2) + 1):
for j in range((i * (i + 1)) << 1,
int(MAX / 2) + 1, 2 * i + 1):
marked[j] = True;
# Since 2 is a prime number
primes.append(2);
# Print other primes. Remaining primes
# are of the form 2*i + 1 such that
# marked[i] is false.
for i in range(1, int(MAX / 2) + 1):
if (marked[i] == False):
primes.append(2 * i + 1);
# Returns true if n is a Equidigital
# number, else false.
def isEquidigital(n):
if (n == 1):
return True;
# Count digits in original number
original_no = n;
sumDigits = 0;
while (original_no > 0):
sumDigits += 1;
original_no = int(original_no / 10);
# Count all digits in prime factors of n
# pDigit is going to hold this value.
pDigit = 0;
count_exp = 0;
p = 0;
i = 0;
while (primes[i] <= int(n / 2)):
# Count powers of p in n
while (n % primes[i] == 0):
# If primes[i] is a prime factor,
p = primes[i];
n = int(n / p);
# Count the power of prime factors
count_exp += 1;
# Add its digits to pDigit.
while (p > 0):
pDigit += 1;
p = int(p / 10);
# Add digits of power of prime
# factors to pDigit.
while (count_exp > 1):
pDigit += 1;
count_exp = int(count_exp / 10);
i += 1;
# If n!=1 then one prime factor
# still to be summed up;
if (n != 1):
while (n > 0):
pDigit += 1;
n = int(n / 10);
# If digits in prime factors and
# digits in original number are same,
# then return true. Else return false.
return (pDigit == sumDigits);
# Driver code
# Finding all prime numbers before
# limit. These numbers are used to
# find prime factors.
sieveSundaram();
print("Printing first few Equidigital",
"Numbers using isEquidigital()");
for i in range(1, 20):
if (isEquidigital(i)):
print(i, end = " ");
# This code is contributed by mits
C#
// C# program to find Equidigital Numbers till n
using System;
using System.Collections;
public class GFG
{
static int MAX = 10000;
static ArrayList primes = new ArrayList(MAX+1);
// Utility function for sieve of sundaram
static void sieveSundaram()
{
// In general Sieve of Sundaram, produces primes smaller
// than (2*x + 2) for a number given number x. Since
// we want primes smaller than MAX, we reduce MAX to half
// This array is used to separate numbers of the form
// i+j+2ij from others where 1 <= i <= j
bool[] marked = new bool[MAX/2 + 1];
// Main logic of Sundaram. Mark all numbers which
// do not generate prime number by doing 2*i+1
for (int i=1; i<=(Math.Sqrt(MAX)-1)/2; i++)
for (int j=(i*(i+1))<<1; j<=MAX/2; j=j+2*i+1)
marked[j] = true;
// Since 2 is a prime number
primes.Add(2);
// Print other primes. Remaining primes are of the
// form 2*i + 1 such that marked[i] is false.
for (int i=1; i<=MAX/2; i++)
if (marked[i] == false)
primes.Add(2*i + 1);
}
// Returns true if n is a Equidigital number, else
// false.
static bool isEquidigital(int n)
{
if (n == 1)
return true;
// Count digits in original number
int original_no = n;
int sumDigits = 0;
while (original_no > 0)
{
sumDigits++;
original_no = original_no/10;
}
// Count all digits in prime factors of n
// pDigit is going to hold this value.
int pDigit = 0 , count_exp = 0, p = 0;
for (int i = 0; (int)primes[i] <= n/2; i++)
{
// Count powers of p in n
while (n % (int)primes[i] == 0)
{
// If primes[i] is a prime factor,
p = (int)primes[i];
n = n/p;
// Count the power of prime factors
count_exp++;
}
// Add its digits to pDigit.
while (p > 0)
{
pDigit++;
p = p / 10;
}
// Add digits of power of prime factors to pDigit.
while (count_exp > 1)
{
pDigit++;
count_exp = count_exp / 10;
}
}
// If n!=1 then one prime factor still to be
// summed up;
if (n != 1)
{
while (n > 0)
{
pDigit++;
n = n/10;
}
}
// If digits in prime factors and
// digits in original number are same, then
// return true. Else return false.
return (pDigit == sumDigits);
}
// Driver method
public static void Main()
{
// Finding all prime numbers before limit. These
// numbers are used to find prime factors.
sieveSundaram();
Console.WriteLine("Printing first few Equidigital Numbers using isEquidigital()");
for (int i=1; i<20; i++)
if (isEquidigital(i))
Console.Write(i + " ");
}
}
// This Code is contributed by mits
PHP
0)
{
$sumDigits++;
$original_no = (int)($original_no/10);
}
// Count all digits in prime factors of n
// pDigit is going to hold this value.
$pDigit = 0;
$count_exp = 0;
$p=0;
for ($i = 0; $primes[$i] <= (int)($n/2); $i++)
{
// Count powers of p in n
while ($n % $primes[$i] == 0)
{
// If primes[i] is a prime factor,
$p = $primes[$i];
$n = (int)($n/$p);
// Count the power of prime factors
$count_exp++;
}
// Add its digits to pDigit.
while ($p > 0)
{
$pDigit++;
$p =(int)($p / 10);
}
// Add digits of power of prime factors to pDigit.
while ($count_exp > 1)
{
$pDigit++;
$count_exp = (int)($count_exp / 10);
}
}
// If n!=1 then one prime factor still to be
// summed up;
if ($n != 1)
{
while ($n > 0)
{
$pDigit++;
$n = (int)($n/10);
}
}
// If digits in prime factors and
// digits in original number are same, then
// return true. Else return false.
return ($pDigit == $sumDigits);
}
// Driver code
// Finding all prime numbers before limit. These
// numbers are used to find prime factors.
sieveSundaram();
echo "Printing first few Equidigital Numbers using isEquidigital()\n";
for ($i=1; $i<20; $i++)
if (isEquidigital($i))
echo $i." ";
// This code is contributed by mits
?>
输出:
Printing first few Equidigital Numbers using isEquidigital()
1 2 3 5 7 10 11 13 14 15 16 17 19
参考 :
https://zh.wikipedia.org/wiki/Equidigital_number