pythonpython-typing

How to change the list[str] annotation so that it accepts list[LiteralString] too?


I have a function that takes a list of str as an input

def function(names: list[str]) -> None:
  for name in names:
    print(name)

If I generate the list using the split() function, I end up with an object of type list[LiteralString] so mypy marks it an error

names = "Jürgen Klopp".split()
function(names)  # Argument of type "list[LiteralString]" cannot be assigned to parameter "names" of type "list[str]" in function "function"

I would like to know how the LiteralString is expected to be used with lists?

I can build myself a type like

StrListType = list[str] | list[LiteralString]

but this workaround is not needed when using non-listed objects, i.e.,

def fn(name: str):
  print(name)

names = "Jürgen Klopp".split()
given_name: LiteralString = names[0]
fn(given_name)  # No problems

Solution

  • You can use a covariant type like Sequence[str], it is a clean solution because it lets your function accept any sequence of strings including the list returned by .split()

    
    from collections.abc import Sequence
    
    def print_names(names: Sequence[str]) -> None:
        for name in names:
            print(name)
    
    names = "Jürgen Klopp".split()
    print_names(names)
    

    Output

    Jürgen
    Klopp