Подсказки типа и переназначение переменных с другим типом

#python #type-hinting

#python #подсказки типа

Вопрос:

Я получаю сообщение об ошибке Incompatible types in assignment (expression has type "str", variable has type "bytes") в приведенном ниже коде.

 import sys

from typing import BinaryIO


def fn1(stream: BinaryIO = sys.stdin.buffer):
    for line in stream:
        line = line.decode('utf-8').replace(' ', '').strip()  # <- error here
        x, y = line.split('|')  # <- error here
        print(x, y)

if __name__ == '__main__':
    fn1()
  

вывод mypy:

 script.py:8: error: Incompatible types in assignment (expression has type "str", variable has type "bytes")
script.py:10: error: Argument 1 to "split" of "bytes" has incompatible type "str"; expected "Optional[bytes]"
Found 2 errors in 1 file (checked 1 source file)
  

Как предложить mypy, чтобы строка была строкой, а не байтами? Я не хочу реорганизовывать код и добавлять новую строку… он же:

 line = line.decode('utf-8')  # new line ... but its works
line = line.replace(' ', '')
  

Комментарии:

1. Невозможно воспроизвести это, пожалуйста, предоставьте больше контекста и ошибку вывода

2. Я думаю, что он жалуется на чтение буфера (который является байтами) в виде строки во время выполнения for line in stream . Попробуйте это: for line in stream.decode('utf-8').split('n')

Ответ №1:

Это невозможно.

Таким образом, самое простое решение — использовать разные имена для разных типов.

 for b_line in stream:
    line = b_line.decode('utf-8').replace(' ', '').strip()
  

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

 while ...:
   a = 's'
   ...possible break...
   a = 1

a   2  # impossible to verify correctness
  

Комментарии:

1. Спасибо, я не хочу проводить рефакторинг кода. Но, видимо, это необходимо.