简体   繁体   中英

how get list of all the possible combinations of 4 digit numbers whose individual digit sum is 13 and last digit is 5 in that number

How get all the possible combinations of 4 digit numbers whose individual digit sum is 13 and last digit is 5 in that number?

I am trying it in python as:

nmz = []
for i in range(1000,10000):
    if ((sum(int(j) for j in str(i))==13) & (i % 10)):
        nmz = nmz.append(i)
        return(nmz)
    else:
        continue

I am getting errors and not able to get expected output:

nmz = [1165,    1345,   1435,   1615,   1705,   2245,   2425,   3055 ..... ]

errors are:

  1. no output as expected
  2. SyntaxError: 'return' outside function

There's no point in starting the range at 1000 because it doesn't fulfil the significant criterion that the number should end with 5. So, start at 1005 and increment by 10. Therefore:

mylist = []
for i in range(1_005, 10_000, 10):
    if sum(int(d) for d in str(i)) == 13:
        mylist.append(i)

print(mylist)

Output:

[1075, 1165, 1255, 1345, 1435, 1525, 1615, 1705, 2065, 2155, 2245, 2335, 2425, 2515, 2605, 3055, 3145, 3235, 3325, 3415, 3505, 4045, 4135, 4225, 4315, 4405, 5035, 5125, 5215, 5305, 6025, 6115, 6205, 7015, 7105, 8005]

Faster alternative using itertools.product which doesn't require the int -> str conversion:

from itertools import product

[sum(a*10**b for a,b in zip(reversed(i), range(len(i))))  # decimal integer from individual integers
 for i in product(range(1,10), range(10), range(10), [5]) # all combinations
 if sum(i)==13]                                           # condition to keep

output:

[1075, 1165, 1255, 1345, 1435, 1525, 1615, 1705, 2065, 2155, 2245, 2335, 2425, 2515, 2605, 3055, 3145, 3235, 3325, 3415, 3505, 4045, 4135, 4225, 4315, 4405, 5035, 5125, 5215, 5305, 6025, 6115, 6205, 7015, 7105, 8005]

Version for any number of digits:

from itertools import product

DIGITS = 4

[sum(a*10**b for a,b in zip(reversed(i), range(len(i))))
 for i in product(range(1,10), *([range(10)]*(DIGITS-2)), [5])
 if sum(i)==13]

This answer and particularly the suggestion in the comments by @keyllbundy are much faster than other currently posted answers and these techniques of leveraging itertools should be understood by all python users. If you want to see how much faster they are, you can use the timeit module like:

import timeit

setup = """
import itertools

def olvin_roght():
    mylist = []
    for i in range(1_005, 10_000, 10):
        if sum(int(d) for d in str(i)) == 13:
            mylist.append(i)
    return mylist

def jonsg():
    return [10*i+5 for i in range(100, 1000) if sum(int(j) for j in str(i)) == 8]

def mozway():
    DIGITS = 4
    return [
        sum(a*10**b for a,b in zip(reversed(i), range(len(i))))
        for i in itertools.product(range(1,10), *([range(10)]*(DIGITS-2)), [5])
        if sum(i)==13
    ] 

def kelly_bundy():
    return [(1+a) * 1000 + (b-a) * 100 + (7-b) * 10 + 5
            for a, b in itertools.combinations_with_replacement(range(8), 2)]
"""
print(f"olvin_roght: {timeit.timeit('olvin_roght()', setup=setup, number=10_000)}")
print(f"jonsg: {timeit.timeit('jonsg()', setup=setup, number=10_000)}")
print(f"mozway: {timeit.timeit('mozway()', setup=setup, number=10_000)}")
print(f"kelly_bundy: {timeit.timeit('kelly_bundy()', setup=setup, number=10_000)}")

This should show you results like:

olvin_roght: 8.36
jonsg: 7.19
mozway: 1.70
kelly_bundy: 0.08

A slightly alternate approach would be to reframe the questions from:

Get a list of all the possible combinations of 4 digit numbers whose individual digits sum to 13 and last digit is 5

as:

Get all 3 digit numbers whose sum is 8.

Then we can do:

results = [i*10+5 for i in range(100, 1000) if sum(int(j) for j in str(i)) == 8]

or formatted a bit as:

results = [
    i * 10 + 5
    for i
    in range(100, 1000)
    if 8 == sum(
            int(j)
            for j
            in str(i)
        )
]

Also giving us:

[1075, 1165, 1255, 1345, 1435, 1525, 1615, 1705, 2065, 2155, 2245, 2335, 2425, 2515, 2605, 3055, 3145, 3235, 3325, 3415, 3505, 4045, 4135, 4225, 4315, 4405, 5035, 5125, 5215, 5305, 6025, 6115, 6205, 7015, 7105, 8005]

you can find all of the answers with:

nums = []
for i in range(1000,10000):
    sumi = (sum([int(j) for j in str(i)])) # sum of i digits
    i_l = i % 10 # i last digit
    if i_l == 5 and sumi == 13:
        nums.append(i)

print (nums)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM