<SYSTEM_TASK:>
Solve the following problem using Python, implementing the functions described below, one line at a time
<END_TASK>
<USER_TASK:>
Description:
 def assert_type(lst_or_dct, keys, exp_types, must_exist=True, check=None):
 """ Raise MetainfoError is not of a particular type lst_or_dct: list or dict instance value exp_types: Sequence of types that the value specified by `keys` must be an instance of must_exist: Whether to raise MetainfoError if `keys` does not resolve to a value check: Callable that gets the value specified by `keys` and returns True if it OK, False otherwise """

    keys = list(keys)
    keychain = []
    while len(keys[:-1]) > 0:
        key = keys.pop(0)
        try:
            lst_or_dct = lst_or_dct[key]
        except (KeyError, IndexError):
            break
        keychain.append(key)

    keychain_str = ''.join(f'[{key!r}]' for key in keychain)
    key = keys.pop(0)

    if not key_exists_in_list_or_dict(key, lst_or_dct):
        if not must_exist:
            return
        raise error.MetainfoError(f"Missing {key!r} in {keychain_str}")

    elif not isinstance(lst_or_dct[key], exp_types):
        exp_types_str = ' or '.join(t.__name__ for t in exp_types)
        type_str = type(lst_or_dct[key]).__name__
        raise error.MetainfoError(f"{keychain_str}[{key!r}] must be {exp_types_str}, "
                                  f"not {type_str}: {lst_or_dct[key]!r}")

    elif check is not None and not check(lst_or_dct[key]):
        raise error.MetainfoError(f"{keychain_str}[{key!r}] is invalid: {lst_or_dct[key]!r}")