#!/usr/bin/env python3 import doctest def build_suffix_array(input_string: str) -> list[int]: """ Build the suffix array for the given string. Parameters: input_string (str): The input string. Returns: list[int]: The suffix array (a list of starting indices of suffixes in sorted order). Examples: >>> build_suffix_array("banana") [5, 3, 1, 0, 4, 2] """ suffixes = [(input_string[i:], i) for i in range(len(input_string))] suffixes.sort() # Sort the suffixes lexicographically suffix_array = [suffix[1] for suffix in suffixes] return suffix_array def build_lcp_array(input_string: str, suffix_array: list[int]) -> list[int]: """ Build the LCP array for the given string and suffix array. Parameters: input_string (str): The input string. suffix_array (list[int]): The suffix array. Returns: list[int]: The LCP array. Examples: >>> suffix_array = build_suffix_array("banana") >>> build_lcp_array("banana", suffix_array) [0, 1, 3, 0, 0, 2] """ n = len(input_string) rank = [0] * n lcp = [0] * n # Compute the rank of each suffix for i, suffix_index in enumerate(suffix_array): rank[suffix_index] = i # Compute the LCP array h = 0 for i in range(n): if rank[i] > 0: j = suffix_array[rank[i] - 1] while ( (i + h < n) and (j + h < n) and (input_string[i + h] == input_string[j + h]) ): h += 1 lcp[rank[i]] = h if h > 0: h -= 1 # Decrease h for the next suffix return lcp # Example usage if __name__ == "__main__": s = "banana" suffix_array = build_suffix_array(s) lcp_array = build_lcp_array(s, suffix_array) print("Suffix Array:") for i in range(len(suffix_array)): print(f"{suffix_array[i]}: {s[suffix_array[i]:]}") print("\nLCP Array:") for i in range(1, len(lcp_array)): lcp_info = ( f"LCP between {s[suffix_array[i - 1]:]} and " f"{s[suffix_array[i]]}: {lcp_array[i]}" ) print(lcp_info) # Run doctests if __name__ == "__main__": doctest.testmod()