def extract_words(crossword, separator = "#"):
    """List words needed to colve the crossword
    :param crossword: puzzle to extract words from
    :param separator: character used as BLANK
    :raise ValueError: if arguments have incorrect value
    :raise TypeError: if arguments have incorrect type
    :returns: list of words serted from shortest to longest alphabetically
    """
    if (type(crossword) is not list) or (False in [type(row) is list for row in crossword]):
        raise TypeError("Incorrect type of crossword")
    height = len(crossword)
    width = len(crossword[0])
    if (False in [len(row) == width for row in crossword]):
        raise ValueError("Crossword is not matrix")
    if not (separator.isascii() and len(separator)==1):
        raise TypeError("Separator has to be single character")
    
    words = []
    for i in range(height):
        for j in range(width):
            #vertical
            if (0==i or separator==crossword[i-1][j]) and separator!=crossword[i][j]:
                length = 1
                while i + length < height and separator!=crossword[i+length][j]:
                    length+=1
                if 1 < length:
                    words.append("".join([crossword[i+x][j] for x in range(length)]))
            #horizontal
            if (0==j or separator==crossword[i][j-1]) and separator!=crossword[i][j]:
                length = 1
                while j + length < width and separator!=crossword[i][j+length]:
                    length+=1
                if 1 < length:
                    words.append("".join(crossword[i][j:(j+length)]))
                    
    words.sort(key = lambda word:(len(word),word))
    
    return words