12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758 |
- class Abbreviator:
- """
- Abbreviates strings to target_length
- """
- def __init__(self, target_length: int):
- if target_length < 1:
- raise ValueError("target_length must be greater than 0.")
- self.target_len = target_length
- def abbreviate(self, input_sent) -> str:
- """
- Abbreviates an input string, prioritizing minimizing length of longest word.
- Given instance `target_length` smaller than possible with min token word length of 1,
- returns smallest possible output given max per-token length of 1.
- :param input_sent
- :return: str string of abbreviated words
- """
- current_length = len(input_sent)
- if current_length <= self.target_len:
- return input_sent
- words = {word: i for i, word in enumerate(input_sent.split())}
- # store result list for downstream in-place token replacement
- result = [word for word in words]
- while current_length > self.target_len:
- sorted_words = [word for word in sorted(words.keys(), key=len, reverse=True)]
- longest_word = sorted_words[0]
- if len(longest_word) == 1:
- return self._re_assemble(words, result)
- words[longest_word[:-1]] = words.pop(longest_word)
- current_length -= 1
- if current_length <= self.target_len:
- return self._re_assemble(words, result)
- for k, v in words.items():
- result[v] = k
- return ' '.join(result)
- @staticmethod
- def _re_assemble(words, result):
- """
- Re-assembles list of words into a string in original order
- :param words:
- :param result:
- :return:
- """
- for k, v in words.items():
- result[v] = k
- return ' '.join(result)
|