input: from typing import List
  from random import randint
  from collections import defaultdict
  from math import inf
  def minimum_cost_to_construct_target(target: str, words: List[str], costs: List[int]) -> int:
      """
      Given a target string, an array of strings 'words', and an integer array 'costs', all of which are of equal length.
  
      Start with an empty string s.
  
      Perform the following operation as many times as needed:
  
      Choose an index i from the range [0, words.length - 1].
      Append words[i] to s.
      The operation cost is costs[i].
      Return the least cost to make s exactly the same as target. If impossible, return -1.
  
      Examples:
      >>> target = "abcdef", words = ["abdef","abc","d","def","ef"], costs = [100,1,1,10,5]
      7
      >>> target = "aaaa", words = ["z","zz","zzz"], costs = [1,10,100]
      -1
  
      Constraints:
      1 <= target.length <= 5 * 10^4
      1 <= words.length == costs.length <= 5 * 10^4
      1 <= words[i].length <= target.length
      The total sum of words[i].length is less than or equal to 5 * 10^4.
      target and words[i] consist only of lowercase English letters.
      1 <= costs[i] <= 10^4
      """
output:     
      dp = [inf] * (len(target) + 1)
      dp[0] = 0
      
      for i in range(1, len(target) + 1):
          for j, word in enumerate(words):
              if i >= len(word) and target[i-len(word):i] == word:
                  dp[i] = min(dp[i], dp[i-len(word)] + costs[j])
                  
      answer = dp[len(target)]
      return answer if answer != inf else -1
  