给定数字总和和数字的平方和 。查找具有给定数字总和和数字平方和的最小数字。该数字不能超过100位数字。如果不存在这样的数字或位数大于100,则打印-1。
例子:
Input : a = 18, b = 162
Output : 99
Explanation : 99 is the smallest possible number whose sum of digits = 9 + 9 = 18 and sum of squares of digits is 92+92 = 162.
Input : a = 12, b = 9
Output : -1
方法:
由于最小的数字可以是100位数字,因此无法存储。因此,解决该问题的第一步将是找到最小的位数,该位数可以使我们得出位数的总和为和数字平方的总和为 。要找到最小位数,我们可以使用动态编程。 DP [a] [b]表示一个数字的最小位数,该数字的总和为和数字的平方和将是 。如果不存在任何这样的数字,则DP [a] [b]将为-1。
由于该数字不能超过100位,因此DP数组的大小将为101 * 8101 。迭代每个数字,然后尝试所有可能的数字组合,这将使我们得出的数字总和为和数字平方的总和为 。使用以下重复关系将最小位数存储在DP [a] [b]中:
DP[a][b] = min( minimumNumberOfDigits(a – i, b – (i * i)) + 1 )
where 1<=i<=9
获得最小位数后,找到数字。要查找数字,请检查所有组合并打印满足以下条件的数字:
1 + dp[a – i][b – i * i] == dp[a][b]
where 1<=i<=9
如果i满足上述条件,则减小通过我和由我和我打破。继续重复上述过程以查找所有数字,直到是0并且是0。
下面是上述方法的实现:
C++
// CPP program to find the Smallest number
// with given sum of digits and
// sum of square of digits
#include
using namespace std;
int dp[901][8101];
// Top down dp to find minimum number of digits with
// given sum of dits a and sum of square of digits as b
int minimumNumberOfDigits(int a, int b)
{
// Invalid condition
if (a > b || a < 0 || b < 0 || a > 900 || b > 8100)
return -1;
// Number of digits satisfied
if (a == 0 && b == 0)
return 0;
// Memoization
if (dp[a][b] != -1)
return dp[a][b];
// Initialize ans as maximum as we have to find the
// minimum number of digits
int ans = 101;
// Check for all possible combinations of digits
for (int i = 9; i >= 1; i--) {
// recurrence call
int k = minimumNumberOfDigits(a - i, b - (i * i));
// If the combination of digits cannot give sum as a
// and sum of square of digits as b
if (k != -1)
ans = min(ans, k + 1);
}
// Returns the minimum number of digits
return dp[a][b] = ans;
}
// Function to print the digits that gives
// sum as a and sum of square of digits as b
void printSmallestNumber(int a,int b)
{
// initialize the dp array as -1
memset(dp, -1, sizeof(dp));
// base condition
dp[0][0] = 0;
// function call to get the minimum number of digits
int k = minimumNumberOfDigits(a, b);
// When there does not exists any number
if (k == -1 || k > 100)
cout << "-1";
else {
// Printing the digits from the most significant digit
while (a > 0 && b > 0) {
// Trying all combinations
for (int i = 1; i <= 9; i++) {
// checking conditions for minimum digits
if (a >= i && b >= i * i &&
1 + dp[a - i][b - i * i] == dp[a][b]) {
cout << i;
a -= i;
b -= i * i;
break;
}
}
}
}
}
// Driver Code
int main()
{
int a = 18, b = 162;
// Function call to print the smallest number
printSmallestNumber(a,b);
}
Java
import java.util.Arrays;
// Java program to find the Smallest number
// with given sum of digits and
// sum of square of digits
class GFG {
static int dp[][] = new int[901][8101];
// Top down dp to find minimum number of digits with
// given sum of dits a and sum of square of digits as b
static int minimumNumberOfDigits(int a, int b) {
// Invalid condition
if (a > b || a < 0 || b < 0 || a > 900 || b > 8100) {
return -1;
}
// Number of digits satisfied
if (a == 0 && b == 0) {
return 0;
}
// Memoization
if (dp[a][b] != -1) {
return dp[a][b];
}
// Initialize ans as maximum as we have to find the
// minimum number of digits
int ans = 101;
// Check for all possible combinations of digits
for (int i = 9; i >= 1; i--) {
// recurrence call
int k = minimumNumberOfDigits(a - i, b - (i * i));
// If the combination of digits cannot give sum as a
// and sum of square of digits as b
if (k != -1) {
ans = Math.min(ans, k + 1);
}
}
// Returns the minimum number of digits
return dp[a][b] = ans;
}
// Function to print the digits that gives
// sum as a and sum of square of digits as b
static void printSmallestNumber(int a, int b) {
// initialize the dp array as -1
for (int[] row : dp) {
Arrays.fill(row, -1);
}
// base condition
dp[0][0] = 0;
// function call to get the minimum number of digits
int k = minimumNumberOfDigits(a, b);
// When there does not exists any number
if (k == -1 || k > 100) {
System.out.println("-1");
} else {
// Printing the digits from the most significant digit
while (a > 0 && b > 0) {
// Trying all combinations
for (int i = 1; i <= 9; i++) {
// checking conditions for minimum digits
if (a >= i && b >= i * i
&& 1 + dp[a - i][b - i * i] == dp[a][b]) {
System.out.print(i);
a -= i;
b -= i * i;
break;
}
}
}
}
}
// Driver Code
public static void main(String args[]) {
int a = 18, b = 162;
// Function call to print the smallest number
printSmallestNumber(a, b);
}
}
// This code is contributed by PrinciRaj19992
Python3
# Python3 program to find the Smallest number
# with given sum of digits and
# sum of square of digits
dp=[[-1 for i in range(8101)]for i in range(901)]
# Top down dp to find minimum number of digits with
# given sum of dits a and sum of square of digits as b
def minimumNumberOfDigits(a,b):
# Invalid condition
if (a > b or a < 0 or b < 0 or a > 900 or b > 8100):
return -1
# Number of digits satisfied
if (a == 0 and b == 0):
return 0
# Memoization
if (dp[a][b] != -1):
return dp[a][b]
# Initialize ans as maximum as we have to find the
# minimum number of digits
ans = 101
#Check for all possible combinations of digits
for i in range(9,0,-1):
# recurrence call
k = minimumNumberOfDigits(a - i, b - (i * i))
# If the combination of digits cannot give sum as a
# and sum of square of digits as b
if (k != -1):
ans = min(ans, k + 1)
# Returns the minimum number of digits
dp[a][b] = ans
return ans
# Function to print the digits that gives
# sum as a and sum of square of digits as b
def printSmallestNumber(a,b):
# initialize the dp array as
for i in range(901):
for j in range(8101):
dp[i][j]=-1
# base condition
dp[0][0] = 0
# function call to get the minimum number of digits
k = minimumNumberOfDigits(a, b)
# When there does not exists any number
if (k == -1 or k > 100):
print(-1,end='')
else:
# Printing the digits from the most significant digit
while (a > 0 and b > 0):
# Trying all combinations
for i in range(1,10):
#checking conditions for minimum digits
if (a >= i and b >= i * i and
1 + dp[a - i][b - i * i] == dp[a][b]):
print(i,end='')
a -= i
b -= i * i
break
# Driver Code
if __name__=='__main__':
a = 18
b = 162
# Function call to print the smallest number
printSmallestNumber(a,b)
# This code is contributed by sahilshelangia
C#
// C# program to find the Smallest number
// with given sum of digits and
// sum of square of digits
using System;
public class GFG {
static int [,]dp = new int[901,8101];
// Top down dp to find minimum number of digits with
// given sum of dits a and sum of square of digits as b
static int minimumNumberOfDigits(int a, int b) {
// Invalid condition
if (a > b || a < 0 || b < 0 || a > 900 || b > 8100) {
return -1;
}
// Number of digits satisfied
if (a == 0 && b == 0) {
return 0;
}
// Memoization
if (dp[a,b] != -1) {
return dp[a,b];
}
// Initialize ans as maximum as we have to find the
// minimum number of digits
int ans = 101;
// Check for all possible combinations of digits
for (int i = 9; i >= 1; i--) {
// recurrence call
int k = minimumNumberOfDigits(a - i, b - (i * i));
// If the combination of digits cannot give sum as a
// and sum of square of digits as b
if (k != -1) {
ans = Math.Min(ans, k + 1);
}
}
// Returns the minimum number of digits
return dp[a,b] = ans;
}
// Function to print the digits that gives
// sum as a and sum of square of digits as b
static void printSmallestNumber(int a, int b) {
// initialize the dp array as -1
for (int i = 0; i < dp.GetLength(0); i++)
for (int j = 0; j < dp.GetLength(1); j++)
dp[i, j] = -1;
// base condition
dp[0,0] = 0;
// function call to get the minimum number of digits
int k = minimumNumberOfDigits(a, b);
// When there does not exists any number
if (k == -1 || k > 100) {
Console.WriteLine("-1");
} else {
// Printing the digits from the most significant digit
while (a > 0 && b > 0) {
// Trying all combinations
for (int i = 1; i <= 9; i++) {
// checking conditions for minimum digits
if (a >= i && b >= i * i
&& 1 + dp[a - i,b - i * i] == dp[a,b]) {
Console.Write(i);
a -= i;
b -= i * i;
break;
}
}
}
}
}
// Driver Code
public static void Main() {
int a = 18, b = 162;
// Function call to print the smallest number
printSmallestNumber(a, b);
}
}
// This code is contributed by PrinciRaj19992
99
时间复杂度:O(900 * 8100 * 9)
辅助空间:O(900 * 8100)
注意:时间复杂度以数字表示,因为我们正在尝试所有可能的数字组合。