# Count of integers from the range [0, N] whose digit sum is a multiple of K

Given two integers N and K, the task is to calculate the number of integers in the range [0, N] whose digit sum is a multiple of K. The answer could be large, so print the answer modulo 109 +7.

Examples:

Input: N = 10, K = 5
Output: 2
0 and 5 are the only possible integers.

Input: N = 30, K = 4
Output: 7

## Recommended: Please try your approach on {IDE} first, before moving on to the solution.

Naive Approach: For small value of N, loop through the range [0, N] and check if the sum of the digits of the numbers are multiples of K or not.

Efficient Approach: The idea is to use digit dp to solve this problem. Subproblems iterating through all index value from left or most significant digit(MSD) in the given integer will be solved and for each index, store the number of ways such that (sum of digits upto current index) mod K to be zero. The dp states will be:

dp[idx][sum][tight]
idx = position, it tells about the index value from left in the given integer
sum = sum of digits mod k, This parameter will store the (sum of digits mod k) in the generated integer from most significant digit(MSD) to p
tight = flag if the current value is crossing the range (1, n) or not
For unrestricted range tight = 0
For restricted range tight = 1

Let’s say we are at the MSD having index idx. So initially the sum will be 0. At every position, set a limit that is always in the range [0, 9].
Therefore, fill the digit at index by the digits in its range from 0 to limit and fetch the answer from the next state having index = idx + 1 and new_tight for next state is calculated separately. The dp state definition will be:

dp[idx][sum][tight] += dp[idx + 1][(sum + d) % k][new_tight]
for d in [0, limit]

Below is the implementation of the above approach:

## C++

 `// C++ implementation of the approach ` `#include ` `using` `namespace` `std; ` ` `  `#define MAX 100005 ` `#define MOD 1000000007 ` ` `  `// To store the states of the dp ` `int` `dp[MAX]; ` ` `  `// Function to return the count of numbers ` `// from the range [0, n] whose digit sum ` `// is a multiple of k using bottom-up dp ` `int` `countNum(``int` `idx, ``int` `sum, ``int` `tight, ` `             ``vector<``int``> num, ``int` `len, ``int` `k) ` `{ ` `    ``if` `(len == idx) { ` `        ``if` `(sum == 0) ` `            ``return` `1; ` `        ``else` `            ``return` `0; ` `    ``} ` `    ``if` `(dp[idx][sum][tight] != -1) ` `        ``return` `dp[idx][sum][tight]; ` `    ``int` `res = 0, limit; ` ` `  `    ``// The digit in this index can ` `    ``// only be from [0, num[idx]] ` `    ``if` `(tight == 0) { ` `        ``limit = num[idx]; ` `    ``} ` ` `  `    ``// The digit in this index can ` `    ``// be anything from [0, 9] ` `    ``else` `{ ` `        ``limit = 9; ` `    ``} ` `    ``for` `(``int` `i = 0; i <= limit; i++) { ` ` `  `        ``// new_tight is the flag value ` `        ``// for the next position ` `        ``int` `new_tight = tight; ` `        ``if` `(tight == 0 && i < limit) ` `            ``new_tight = 1; ` `        ``res += countNum(idx + 1, ` `                        ``(sum + i) % k, new_tight, ` `                        ``num, len, k); ` `        ``res %= MOD; ` `    ``} ` ` `  `    ``// res can't be negative ` `    ``if` `(res < 0) ` `        ``res += MOD; ` `    ``return` `dp[idx][sum][tight] = res; ` `} ` ` `  `// Function to process the string to ` `// a vector of digits from MSD to LSD ` `vector<``int``> process(string s) ` `{ ` `    ``vector<``int``> num; ` `    ``for` `(``int` `i = 0; i < s.length(); i++) { ` `        ``num.push_back(s[i] - ``'0'``); ` `    ``} ` `    ``return` `num; ` `} ` ` `  `// Driver code ` `int` `main() ` `{ ` ` `  `    ``// For large input number n ` `    ``string n = ``"98765432109876543210"``; ` ` `  `    ``// Total number of digits in n ` `    ``int` `len = n.length(); ` ` `  `    ``int` `k = 58; ` ` `  `    ``// Clean dp table ` `    ``memset``(dp, -1, ``sizeof``(dp)); ` ` `  `    ``// Process the string to a vector ` `    ``// of digits from MSD to LSD ` `    ``vector<``int``> num = process(n); ` ` `  `    ``cout << countNum(0, 0, 0, num, len, k); ` ` `  `    ``return` `0; ` `} `

## Java

 `// Java implementation of the approach ` `import` `java.util.*; ` ` `  `class` `GFG ` `{ ` ` `  `static` `final` `int` `MAX = ``100005``; ` `static` `final` `int` `MOD = ``1000000007``; ` ` `  `// To store the states of the dp ` `static` `int` `[][][]dp = ``new` `int``[MAX][``101``][``2``]; ` ` `  `// Function to return the count of numbers ` `// from the range [0, n] whose digit sum ` `// is a multiple of k using bottom-up dp ` `static` `int` `countNum(``int` `idx, ``int` `sum, ``int` `tight, ` `            ``Vector num, ``int` `len, ``int` `k) ` `{ ` `    ``if` `(len == idx)  ` `    ``{ ` `        ``if` `(sum == ``0``) ` `            ``return` `1``; ` `        ``else` `            ``return` `0``; ` `    ``} ` `    ``if` `(dp[idx][sum][tight] != -``1``) ` `        ``return` `dp[idx][sum][tight]; ` `    ``int` `res = ``0``, limit; ` ` `  `    ``// The digit in this index can ` `    ``// only be from [0, num[idx]] ` `    ``if` `(tight == ``0``)  ` `    ``{ ` `        ``limit = num.get(idx); ` `    ``} ` ` `  `    ``// The digit in this index can ` `    ``// be anything from [0, 9] ` `    ``else` `    ``{ ` `        ``limit = ``9``; ` `    ``} ` `    ``for` `(``int` `i = ``0``; i <= limit; i++) ` `    ``{ ` ` `  `        ``// new_tight is the flag value ` `        ``// for the next position ` `        ``int` `new_tight = tight; ` `        ``if` `(tight == ``0` `&& i < limit) ` `            ``new_tight = ``1``; ` `        ``res += countNum(idx + ``1``, ` `                        ``(sum + i) % k, new_tight, ` `                        ``num, len, k); ` `        ``res %= MOD; ` `    ``} ` ` `  `    ``// res can't be negative ` `    ``if` `(res < ``0``) ` `        ``res += MOD; ` `    ``return` `dp[idx][sum][tight] = res; ` `} ` ` `  `// Function to process the String to ` `// a vector of digits from MSD to LSD ` `static` `Vector process(String s) ` `{ ` `    ``Vector num = ``new` `Vector(); ` `    ``for` `(``int` `i = ``0``; i < s.length(); i++) ` `    ``{ ` `        ``num.add(s.charAt(i) - ``'0'``); ` `    ``} ` `    ``return` `num; ` `} ` ` `  `// Driver code ` `public` `static` `void` `main(String[] args) ` `{ ` ` `  `    ``// For large input number n ` `    ``String n = ``"98765432109876543210"``; ` ` `  `    ``// Total number of digits in n ` `    ``int` `len = n.length(); ` ` `  `    ``int` `k = ``58``; ` ` `  `    ``// Clean dp table ` `    ``for``(``int` `i = ``0``; i < MAX; i++) ` `    ``{ ` `        ``for``(``int` `j = ``0``; j < ``101``; j++) ` `        ``{ ` `            ``for``(``int` `l = ``0``; l < ``2``; l++) ` `            ``dp[i][j][l] = -``1``; ` `        ``} ` `    ``} ` ` `  `    ``// Process the String to a vector ` `    ``// of digits from MSD to LSD ` `    ``Vector num = process(n); ` ` `  `    ``System.out.print(countNum(``0``, ``0``, ``0``, num, len, k)); ` ` `  `} ` `} ` ` `  `// This code is contributed by 29AjayKumar `

## Python 3

 `# Python 3 implementation of the approach ` `MAX` `=` `10005` `MOD ``=` `1000000007` ` `  `# Function to return the count of numbers ` `# from the range [0, n] whose digit sum ` `# is a multiple of k using bottom-up dp ` `def` `countNum(idx, ``sum``, tight, num, len1, k): ` `    ``if` `(len1 ``=``=` `idx): ` `        ``if` `(``sum` `=``=` `0``): ` `            ``return` `1` `        ``else``: ` `            ``return` `0` `    ``if` `(dp[idx][``sum``][tight] !``=` `-``1``): ` `        ``return` `dp[idx][``sum``][tight] ` `    ``res ``=` `0` ` `  `    ``# The digit in this index can ` `    ``# only be from [0, num[idx]] ` `    ``if` `(tight ``=``=` `0``): ` `        ``limit ``=` `num[idx] ` ` `  `    ``# The digit in this index can ` `    ``# be anything from [0, 9] ` `    ``else``: ` `        ``limit ``=` `9` `    ``for` `i ``in` `range``(limit ``+` `1``): ` `         `  `        ``# new_tight is the flag value ` `        ``# for the next position ` `        ``new_tight ``=` `tight ` `        ``if` `(tight ``=``=` `0` `and` `i < limit): ` `            ``new_tight ``=` `1` `        ``res ``+``=` `countNum(idx ``+` `1``,(``sum` `+` `i) ``%` `k,  ` `                      ``new_tight, num, len1, k) ` `        ``res ``%``=` `MOD ` ` `  `    ``# res can't be negative ` `    ``if` `(res < ``0``): ` `        ``res ``+``=` `MOD ` `    ``dp[idx][``sum``][tight] ``=` `res ` `    ``return` `dp[idx][``sum``][tight] ` ` `  `# Function to process the string to ` `# a vector of digits from MSD to LSD ` `def` `process(s): ` `    ``num ``=` `[] ` `    ``for` `i ``in` `range``(``len``(s)): ` `        ``num.append(``ord``(s[i]) ``-` `ord``(``'0'``)) ` `    ``return` `num ` ` `  `# Driver code ` `if` `__name__ ``=``=` `'__main__'``: ` `     `  `    ``# For large input number n ` `    ``n ``=` `"98765432109876543210"` ` `  `    ``# Total number of digits in n ` `    ``len1 ``=` `len``(n) ` ` `  `    ``k ``=` `58` `     `  `    ``# To store the states of the dp ` `    ``dp ``=` `[[[``-``1` `for` `i ``in` `range``(``2``)] ` `               ``for` `j ``in` `range``(``101``)]  ` `               ``for` `k ``in` `range``(``MAX``)] ` ` `  `    ``# Process the string to a vector ` `    ``# of digits from MSD to LSD ` `    ``num ``=` `process(n) ` ` `  `    ``print``(countNum(``0``, ``0``, ``0``, num, len1, k)) ` ` `  `# This code is contributed by Surendra_Gangwar `

## C#

 `// C# implementation of the approach ` `using` `System; ` `using` `System.Collections.Generic; ` ` `  `class` `GFG ` `{ ` `static` `readonly` `int` `MAX = 10005; ` `static` `readonly` `int` `MOD = 1000000007; ` ` `  `// To store the states of the dp ` `static` `int` `[,,]dp = ``new` `int``[MAX, 101, 2]; ` ` `  `// Function to return the count of numbers ` `// from the range [0, n] whose digit sum ` `// is a multiple of k using bottom-up dp ` `static` `int` `countNum(``int` `idx, ``int` `sum, ``int` `tight, ` `              ``List<``int``> num, ``int` `len, ``int` `k) ` `{ ` `    ``if` `(len == idx)  ` `    ``{ ` `        ``if` `(sum == 0) ` `            ``return` `1; ` `        ``else` `            ``return` `0; ` `    ``} ` `     `  `    ``if` `(dp[idx, sum, tight] != -1) ` `        ``return` `dp[idx, sum, tight]; ` `    ``int` `res = 0, limit; ` ` `  `    ``// The digit in this index can ` `    ``// only be from [0, num[idx]] ` `    ``if` `(tight == 0)  ` `    ``{ ` `        ``limit = num[idx]; ` `    ``} ` ` `  `    ``// The digit in this index can ` `    ``// be anything from [0, 9] ` `    ``else` `    ``{ ` `        ``limit = 9; ` `    ``} ` `    ``for` `(``int` `i = 0; i <= limit; i++) ` `    ``{ ` ` `  `        ``// new_tight is the flag value ` `        ``// for the next position ` `        ``int` `new_tight = tight; ` `        ``if` `(tight == 0 && i < limit) ` `            ``new_tight = 1; ` `        ``res += countNum(idx + 1, ` `                       ``(sum + i) % k, new_tight, ` `                        ``num, len, k); ` `        ``res %= MOD; ` `    ``} ` ` `  `    ``// res can't be negative ` `    ``if` `(res < 0) ` `        ``res += MOD; ` `    ``return` `dp[idx, sum, tight] = res; ` `} ` ` `  `// Function to process the String to ` `// a vector of digits from MSD to LSD ` `static` `List<``int``> process(String s) ` `{ ` `    ``List<``int``> num = ``new` `List<``int``>(); ` `    ``for` `(``int` `i = 0; i < s.Length; i++) ` `    ``{ ` `        ``num.Add(s[i] - ``'0'``); ` `    ``} ` `    ``return` `num; ` `} ` ` `  `// Driver code ` `public` `static` `void` `Main(String[] args) ` `{ ` ` `  `    ``// For large input number n ` `    ``String n = ``"98765432109876543210"``; ` ` `  `    ``// Total number of digits in n ` `    ``int` `len = n.Length; ` ` `  `    ``int` `k = 58; ` ` `  `    ``// Clean dp table ` `    ``for``(``int` `i = 0; i < MAX; i++) ` `    ``{ ` `        ``for``(``int` `j = 0; j < 101; j++) ` `        ``{ ` `            ``for``(``int` `l = 0; l < 2; l++) ` `            ``dp[i, j, l] = -1; ` `        ``} ` `    ``} ` ` `  `    ``// Process the String to a vector ` `    ``// of digits from MSD to LSD ` `    ``List<``int``> num = process(n); ` ` `  `    ``Console.Write(countNum(0, 0, 0, num, len, k)); ` `} ` `} ` ` `  `// This code is contributed by Rajput-Ji `

Output:

```635270835
```

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the DSA Self Paced Course at a student-friendly price and become industry ready.

My Personal Notes arrow_drop_up Check out this Author's contributed articles.

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.