Почему не работает прерывание клавиатуры Python? (в пичарме)

Мой цикл попытки / исключения в python, по-видимому, не вызывает прерывания клавиатуры при нажатии Ctrl + C во время отладки моего кода в pycharm. Мой код выглядит так:

numbers = []
loop = True

try: 
    # ===========SUBROUTINES==================

    def help():
        print("To view the list type 'view'"
              "\n To add an item type 'add'"
              "\n To remove an item type 'remove'"
              "\n To exit type exit or Ctrl + c can be used at any time")

    # =========SUBROUTENES END===============


    while loop:
        task = input("What do you want to do? Type \"help\" for help:- ")
        if task == 'help':
            help()
        else:
            print("Invalid return please try again.")

    except KeyboardInterrupt:
        exit()

РЕДАКТИРОВАТЬ: Кажется, есть некоторые проблемы с моим уменьшенным кодом работает и не выдает ту же ошибку. Полный код можно посмотреть здесь. Я также повторно уменьшил код (код выше), и он выдал ту же ошибку.

9 ответов

Решение

Из вашего снимка экрана видно, что вы запускаете этот код в IDE. Особенность IDE заключается в том, что они не совсем работают так, как обычно, особенно когда речь идет об обработке символов клавиатуры. То, как вы нажимаете Ctrl-C, ваша IDE думает, что вы хотите скопировать текст. Программа Python никогда не видит персонажа. Возможно, это вызывает отдельное окно при запуске? Затем вы должны выбрать это окно перед Ctrl-C.

Я знаю, что это старый вопрос, но я столкнулся с той же проблемой и думаю, что есть более простое решение:

В PyCharm перейдите в "Выполнить"/"Изменить конфигурации" и установите флажок "Эмулировать терминал в консоли вывода". PyCharm теперь принимает прерывания клавиатуры (убедитесь, что консоль сфокусирована).

Проверено на: PyCharm 2019.1 (Community Edition)

Консоль Python PyCharm вызывает исключение console_thrift.KeyboardInterruptException на Ctrl-C вместо KeyboardInterrupt. Исключение console_thrift.KeyboardInterruptException не является подклассом KeyboardInterrupt, поэтому леска не попадает except KeyboardInterrupt.

Добавление следующих строк сделает ваш скрипт совместимым с PyCharm.

try:
    from console_thrift import KeyboardInterruptException as KeyboardInterrupt
except ImportError:
    pass

Это не нарушит совместимость с запуском сценария в терминале или другой среде IDE, например IDLE или Spyder, поскольку модуль console_thrift находится только в PyCharm.

Вы также можете использовать консоль Python PyCharm и использовать Ctrl + C, если вы поймаете исключение, которое PyCharm вызывает при нажатии Ctrl + C. Ниже я написал короткую функцию под названиемis_keyboard_interruptкоторый сообщает вам, является ли исключение KeyboardInterrupt, включая PyCharm. Если это не так, просто поднимите его заново. Я вставляю упрощенную версию кода ниже.

Когда он запущен:

  • введите help и нажмите Enter, чтобы повторить цикл.
  • введите что-нибудь еще и нажмите Enter, чтобы убедиться, что ValueError обрабатывается правильно.
  • Нажмите Ctrl + C, чтобы проверить, что KeyboardInterrupt перехватывается, в том числе в консоли python PyCharm.

Примечание. Это не работает с консолью отладчика PyCharm (той, которая вызывается командой "Отладка", а не "Выполнить"), но там необходимость в Ctrl + C меньше, потому что вы можете просто нажать кнопку паузы.

Я также помещаю это в свой Gist, где могу делать обновления: https://gist.github.com/yulkang/14da861b271576a9eb1fa0f905351b97

def is_keyboard_interrupt(exception):
    # The second condition is necessary for it to work with the stop button
    # in PyCharm Python console.
    return (type(exception) is KeyboardInterrupt
            or type(exception).__name__ == 'KeyboardInterruptException')

try:
    def print_help():
        print("To exit type exit or Ctrl + c can be used at any time")
    print_help()

    while True:
        task = input("What do you want to do? Type \"help\" for help:- ")
        if task == 'help':
            print_help()
        else:
            print("Invalid input.")

            # to check that ValueError is handled separately
            raise ValueError()

except Exception as ex:
    try:
        # Catch all exceptions and test if it is KeyboardInterrupt, native or
        # PyCharm's.
        if not is_keyboard_interrupt(ex):
            raise ex

        print('KeyboardInterrupt caught as expected.')
        print('Exception type: %s' % type(ex).__name__)
        exit()

    except ValueError:
        print('ValueError!')

Если этот комментарий не решит вашу проблему, (из @tdelaney) вам нужно сфокусировать окно оболочки (то есть вы щелкнули по нему во время работы программы), а затем вы можете использовать Control+C

Попробуйте Shift + Ctrl + C. У меня это сработало.

Здесь работает нормально, так как я помещаю переменную "x" в ваш код и использую табуляцию вместо пробелов.

try:

    def help():
        print("Help.")

    def doStuff():
        print("Doing Stuff")

    while True:
        x = int(input())
        if x == 1:
            help()
        elif x == 2:
            doStuff()
        else:
            exit()

except KeyboardInterrupt:
    exit()

Убедитесь, что окно выбрано, когда вы нажимаете Ctrl+ C. Я просто запустил вашу программу в IDLE, и она отлично сработала для меня.

Одна из возможных причин, по которой <Strg+C> не останавливает программу:

Когда текст отмечен в оболочке, <Strg+C> интерпретируется как «копировать отмеченный текст в буфер обмена».

Просто снимите отметку с текста и снова нажмите <Strg+C>.

Другие вопросы по тегам