Что не так с моим кодом?

есть задача:

Дано число n Ваша задача — найти число из n цифр, каждая из которых равна 1 или 2, которое делится на 2^n, или сказать, что такого числа не существует.

Тест 1: входные данные: 1 выходные данные: 2

Тест 2: входные данные: 2 выходные данные: 12

мой код:

def check(number):
    while number > 0:
        if (0 < number % 10 < 3):
            number //= 10
        else:
            return False
    return True
 
 
n = int(input())
 
template = 2 ** n
number = template
 
while True:
    if (check(number)):
        print(number)
        break
    number += template

что не так?


Ответы (3 шт):

Автор решения: Zhihar

Потому что вы совершенно не то делали

# получить кол-во цифр в числе
digits_count = int(input())

# перебрать все соответствующие числа
res = []

for i in range(10**(digits_count - 1), 10**digits_count - 1):
    # рассматривать только числа, которые делятся на 2^n
    if i % 2**digits_count == 0:
        # определить, содержит ли число цифры отличные от 1 и 2
        value = i
        is_success = True

        while value != 0:
            digit = value % 10
            value //= 10
            if digit != 1 and digit != 2:
                is_success = False
                break

        # добавить найденное число в список
        if is_success is True:
            res.append(i)

# вывести результат
if len(res) == 0:
    print("Нет числа")
else:
    print(*res, sep='\n')

если работать со строками, то можно сделать проверку попроще:

for i in range(10**(digits_count - 1), 10**digits_count - 1):
    # рассматривать только числа, которые делятся на 2^n
    if i % 2**digits_count == 0:
        # определить, содержит ли число цифры отличные от 1 и 2
        digits = list(filter(lambda i: i != '1' and i != '2', set(str(i))))

        # добавить найденное число в список
        if len(digits) == 0:
            res.append(i)

можно ускорить в 3 раза код если уменьшить цикл от 1xxxxx до 2xxxxx

for i in range(10**(digits_count - 1), 3 * 10**(digits_count - 1)):
    # рассматривать только числа, которые делятся на 2^n
    # определить, содержит ли число цифры отличные от 1 и 2
    if i % 2**digits_count == 0 and len(list(filter(lambda i: i != '1' and i != '2', set(str(i))))) == 0:
        # добавить найденное число в список
        if len(list(filter(lambda i: i != '1' and i != '2', set(str(i))))) == 0:
            res.append(i)

можно еще существенно увеличить скорость, если просматривать только числа, которые делятся на 2^n через модификацию for и указания шага в 2^n

в этом случае скорость возрастает так же еще в разы и порядки (в зависимости от кол-ва цифр) + можно улучшить проверку на цифры (от @Danis):

import math

# получить кол-во цифр в числе
digits_count = int(input())

if digits_count < 1:
    print("Нет числа")
    exit()

limit = 2**digits_count

start = math.ceil(10**(digits_count - 1) / limit) * limit

# перебрать все соответствующие числа
res = []

for i in range(start, 3 * 10**(digits_count - 1), limit):
    # определить, содержит ли число цифры отличные от 1 и 2
    if len(list(filter(lambda i: i != '1' and i != '2', set(str(i))))) == 0:
        # добавить найденное число в список
        if len(set(str(i) + '12')) == 2:
            res.append(i)

# вывести результат
if len(res) == 0:
    print("Нет числа")
else:
    print(*res, sep='\n')
→ Ссылка
Автор решения: n1tr0xs

Как вариант:

from itertools import product

digits = ['1', '2']
n = int(input())
if n < 1:
    print('Нет числа')
    exit()

temp = 2**n
for prod in product(digits, repeat=n):
    number = int(''.join(prod))
    if number % temp == 0:
        print(number)
        break
else:
    print('Нет числа')

Так должно быть немного быстрее (не проверяет нечетные числа):

for prod in product(digits, repeat=n-1): # <--------
    number = int(''.join(prod) + '2')    # <--------
    if number % temp == 0:
        print(number)
        break
else:
    print('Нет числа')
→ Ссылка
Автор решения: Danis

У меня получился так:

n = int(input())

if n == 0:
    print("Нет числа")
    exit()

s = ''
for i in range(n):
    if int("1" + s) % (2 << i) == 0:
        s = "1" + s
    else:
        s = "2" + s
    
print(s)
→ Ссылка