Проблема с функцией any() в генераторе паролей (python3)

Есть следующий код:

import random as rnd
from string import ascii_letters, ascii_lowercase, ascii_uppercase, digits


def second_password_generator(main_count, length):
    symbols = "".join((set(ascii_letters) | set(digits)) - set('lI1oO0'))
    for _ in range(main_count):
        count = 3
        password = []
        for _ in range(length):
            password.append(rnd.choice(symbols))
        if any(ascii_uppercase) in password:
            count -= 1
        if any(ascii_lowercase) in password:
            count -= 1
        if any(digits) in password:
            count -= 1
        if count == 0:
            print(*password, sep="")
        else:
            main_count += 1


a, b = [int(input()) for _ in "aa"]
second_password_generator(a, b)

Проблема заключается в том, что он ничего не возвращает т.к не проверяются следующие условия (которые проверяют наличие символов в списке):

if any(ascii_uppercase) in password:
    count -= 1
if any(ascii_lowercase) in password:
    count -= 1
if any(digits) in password:
    count -= 1

А так же не выполняется условие:

else:
    main_count += 1

Что делать?


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

Автор решения: CrazyElf
if any(ascii_uppercase) in password:

any работает не так, как вы думаете. Если любой элемент из переданной ему коллекции True, то он возвращает True, иначе False. Коллекция ascii_uppercase не пустая (при такой проверке строка превращается в коллекцию символов), поэтому any(ascii_uppercase) всегда будет равно True. А далее проверяется - есть ли True в password. Конечно, никакого булевского True нет в строке password (которая в этом случае тоже рассматривается как коллекция символов). Поэтому значение выражения any(ascii_uppercase) in password всегда False, оно никогда не выполняется.

Как же правильно проверить, что в password есть хотя бы один символ ascii_uppercase? Через пересечение множеств. Проверяем, что пересечение множеств символов из этих строк не пустое:

if set(ascii_uppercase) & set(password):

Также можно свести все ваши проверки в одну помощью оператора all:

if all((
    set(ascii_uppercase) & set(password),
    set(ascii_lowercase) & set(password),
    set(digits) & set(password)
   )):
→ Ссылка
Автор решения: pankazimierz

Cпасибо СrazyElf за подсказку, однако задача была выполнена при следеющей реализации:

import random as rnd
from string import ascii_letters, ascii_lowercase, ascii_uppercase, digits


def second_password_generator(main_count, length):
    symbols = "".join((set(ascii_letters) | set(digits)) - set('lI1oO0'))
    for _ in range(main_count):
        password = []
        for _ in range(length - 3):
            password.append(rnd.choice(symbols))
        password.append(rnd.choice("".join(set(ascii_uppercase) - set('lI1oO0'))))
        password.append(rnd.choice("".join(set(ascii_lowercase) - set('lI1oO0'))))
        password.append(rnd.choice("".join(set(digits) - set('lI1oO0'))))
        rnd.shuffle(password)
        print(*password, sep='')


a, b = [int(input()) for _ in "aa"]
second_password_generator(a, b)
→ Ссылка