def tokenize_lisp(lisp_file_name): ws_in_lisp_record = "" ws_lisp_eof = False ws_temp_num = 0 symbol_table = [""] * 100 symbol_lengths = [0] * 100 ls_symbol_table_size = 0 def calc_lisp_length(ws_calc_length_str): ws_lisp_length = 0 ws_num_length_add = 0 ws_is_comment_yes = False for char in ws_calc_length_str: if char == ";": ws_is_comment_yes = True break elif char != " ": ws_lisp_length += 1 ws_lisp_length += ws_num_length_add ws_num_length_add = 0 else: ws_num_length_add += 1 return ws_lisp_length, ws_is_comment_yes def append_lisp_procedure(ws_in_lisp_record, in_lisp_record, ws_temp_num): ws_calc_length_str = in_lisp_record ws_lisp_length, ws_is_comment_yes = calc_lisp_length(ws_calc_length_str) if not ws_is_comment_yes: if ws_temp_num == 0: ws_in_lisp_record = in_lisp_record else: ws_in_lisp_record = ws_in_lisp_record[:ws_temp_num+1] + in_lisp_record[:ws_lisp_length] ws_temp_num -= 1 ws_temp_num += ws_lisp_length return ws_in_lisp_record, ws_temp_num def file_handling_procedure(lisp_file_name, ws_in_lisp_record, ws_temp_num, ws_lisp_eof): try: with open(lisp_file_name, 'r') as lisp_file: in_lisp_record = lisp_file.readline().strip('\n') if not in_lisp_record: ws_lisp_eof = True else: ws_calc_length_str = in_lisp_record ws_lisp_length, ws_is_comment_yes = calc_lisp_length(ws_calc_length_str) if not ws_is_comment_yes: ws_in_lisp_record = in_lisp_record ws_temp_num = ws_lisp_length while not ws_lisp_eof: in_lisp_record = lisp_file.readline().strip('\n') if not in_lisp_record: ws_lisp_eof = True else: ws_in_lisp_record, ws_temp_num = append_lisp_procedure(ws_in_lisp_record, in_lisp_record, ws_temp_num) except FileNotFoundError: print(f"Error: File '{lisp_file_name}' not found.") ws_lisp_eof = True # To stop processing if file not found return ws_in_lisp_record, ws_temp_num, ws_lisp_eof def format_lisp_procedure(ws_in_lisp_record): ws_calc_length_str = ws_in_lisp_record ws_lisp_length, _ = calc_lisp_length(ws_calc_length_str) ws_format_str_index = 1 if ws_in_lisp_record.startswith("(") and (len(ws_in_lisp_record) <= 1 or ws_in_lisp_record[1] != " "): ws_in_lisp_record = "( " + ws_in_lisp_record[1:] ws_format_str_index += 2 ws_lisp_length += 1 ws_format_str_index = 1 formatted_record_list = list(ws_in_lisp_record) lisp_length_dynamic = len(formatted_record_list) while ws_format_str_index <= lisp_length_dynamic: ws_paren_left_yes = False ws_paren_right_yes = False if formatted_record_list[ws_format_str_index-1] == "(": def format_check_paren_procedure(formatted_record_list, ws_format_str_index, lisp_length_dynamic): ws_paren_left_yes = False ws_paren_right_yes = False if ws_format_str_index - 1 - 1 >= 0 and formatted_record_list[ws_format_str_index - 1 - 1] != " ": ws_paren_left_yes = True if ws_format_str_index - 1 + 1 < lisp_length_dynamic and formatted_record_list[ws_format_str_index - 1 + 1] != " ": ws_paren_right_yes = True return ws_paren_left_yes, ws_paren_right_yes def format_add_left_space(formatted_record_list, ws_format_str_index): formatted_record_list.insert(ws_format_str_index - 1, " ") return formatted_record_list def format_add_right_space(formatted_record_list, ws_format_str_index): formatted_record_list.insert(ws_format_str_index, " ") return formatted_record_list def format_add_both_spaces(formatted_record_list, ws_format_str_index): formatted_record_list.insert(ws_format_str_index - 1, " ") formatted_record_list.insert(ws_format_str_index + 1, " ") # index is shifted by previous insert return formatted_record_list ws_paren_left_yes, ws_paren_right_yes = format_check_paren_procedure(formatted_record_list, ws_format_str_index, lisp_length_dynamic) if ws_paren_right_yes and ws_paren_left_yes: formatted_record_list = format_add_both_spaces(formatted_record_list, ws_format_str_index) lisp_length_dynamic += 2 ws_format_str_index += 2 # Skip over added spaces and paren elif ws_paren_right_yes: formatted_record_list = format_add_right_space(formatted_record_list, ws_format_str_index) lisp_length_dynamic += 1 ws_format_str_index += 1 # Skip over added space and paren elif ws_paren_left_yes: formatted_record_list = format_add_left_space(formatted_record_list, ws_format_str_index) lisp_length_dynamic += 1 # ws_format_str_index += 1 No need to increment here as the current char is still paren elif formatted_record_list[ws_format_str_index-1] == ")": def format_check_paren_procedure(formatted_record_list, ws_format_str_index, lisp_length_dynamic): ws_paren_left_yes = False ws_paren_right_yes = False if ws_format_str_index - 1 - 1 >= 0 and formatted_record_list[ws_format_str_index - 1 - 1] != " ": ws_paren_left_yes = True if ws_format_str_index - 1 + 1 < lisp_length_dynamic and formatted_record_list[ws_format_str_index - 1 + 1] != " ": ws_paren_right_yes = True return ws_paren_left_yes, ws_paren_right_yes def format_add_left_space(formatted_record_list, ws_format_str_index): formatted_record_list.insert(ws_format_str_index - 1, " ") return formatted_record_list def format_add_right_space(formatted_record_list, ws_format_str_index): formatted_record_list.insert(ws_format_str_index, " ") return formatted_record_list def format_add_both_spaces(formatted_record_list, ws_format_str_index): formatted_record_list.insert(ws_format_str_index - 1, " ") formatted_record_list.insert(ws_format_str_index + 1, " ") # index is shifted by previous insert return formatted_record_list ws_paren_left_yes, ws_paren_right_yes = format_check_paren_procedure(formatted_record_list, ws_format_str_index, lisp_length_dynamic) if ws_paren_right_yes and ws_paren_left_yes: formatted_record_list = format_add_both_spaces(formatted_record_list, ws_format_str_index) lisp_length_dynamic += 2 ws_format_str_index += 2 # Skip over added spaces and paren elif ws_paren_right_yes: formatted_record_list = format_add_right_space(formatted_record_list, ws_format_str_index) lisp_length_dynamic += 1 ws_format_str_index += 1 # Skip over added space and paren elif ws_paren_left_yes: formatted_record_list = format_add_left_space(formatted_record_list, ws_format_str_index) lisp_length_dynamic += 1 # ws_format_str_index += 1 No need to increment here as the current char is still paren ws_format_str_index += 1 ws_in_lisp_record = "".join(formatted_record_list) return ws_in_lisp_record def tokenize_lisp_procedure(ws_in_lisp_record, symbol_table, ls_symbol_table_size): string_ptr = 0 ls_symbol_table_size = 0 tokens = ws_in_lisp_record.split() for ws_count, token in enumerate(tokens): if ws_count < 100: symbol_table[ls_symbol_table_size] = token ls_symbol_table_size += 1 else: break # Cobol code has limit of 100 symbols return symbol_table, ls_symbol_table_size def calc_length_all_symbols(symbol_table, symbol_lengths, ls_symbol_table_size): for ws_count in range(ls_symbol_table_size): symbol_lengths[ws_count] = calc_length_symbol(symbol_table[ws_count]) return symbol_lengths def calc_length_symbol(symbol): ws_parse_expression_len = 0 for char in symbol: if char == " ": break else: ws_parse_expression_len += 1 return ws_parse_expression_len def print_symbol_table(symbol_table, symbol_lengths, ls_symbol_table_size): for ws_count in range(ls_symbol_table_size): print(ws_count + 1) print(symbol_table[ws_count]) print(symbol_lengths[ws_count]) ws_in_lisp_record, ws_temp_num, ws_lisp_eof = file_handling_procedure(lisp_file_name, ws_in_lisp_record, ws_temp_num, ws_lisp_eof) if not ws_lisp_eof: # Proceed only if file was successfully read ws_in_lisp_record = format_lisp_procedure(ws_in_lisp_record) symbol_table, ls_symbol_table_size = tokenize_lisp_procedure(ws_in_lisp_record, symbol_table, ls_symbol_table_size) symbol_lengths = calc_length_all_symbols(symbol_table, symbol_lengths, ls_symbol_table_size) print_symbol_table(symbol_table, symbol_lengths, ls_symbol_table_size) return symbol_table[:ls_symbol_table_size], symbol_lengths[:ls_symbol_table_size] # Return only filled part of tables if __name__ == '__main__': lisp_file_name = "input.lisp" # Replace with your Lisp file name symbols, lengths = tokenize_lisp(lisp_file_name)