如何在Python中保存先前的”output”或先前输出状态在递归函数调用中?

huangapple go评论119阅读模式
英文:

How to save previous "output" or a state of the previous output in a recursive function call in python?

问题

我正在使用递归函数来生成文本,使用正则表达式匹配,在其中找到一个由方括号内的同义词组合组成的模式(pattern = '[.*?]'),由字符串分隔符分隔(我定义了一个 SEPARATOR =#lkmkmksdmf### )。

函数的初始句子参数类似于:

[decreasing#lkmkmksdmf###shrinking#lkmkmksdmf###falling#lkmkmksdmf###contracting#lkmkmksdmf###faltering#lkmkmksdmf###the contraction in] exports of services will drive national economy to a 0.3% real GDP [decline#lkmkmksdmf###decrease#lkmkmksdmf###contraction] in 2023 from an estimated 5.0% [decline#lkmkmksdmf###decrease#lkmkmksdmf###contraction] in 2022

函数的结构如下:

  1. def combinations(self, sentence, master_sentence_list: list):
  2. pattern = '[.*?]'
  3. if not re.findall(pattern, sentence, flags=re.IGNORECASE):
  4. if sentence not in sentence_list:
  5. sentence_list.append(sentence)
  6. else:
  7. for regex_match in re.finditer(pattern, sentence, flags=re.IGNORECASE):
  8. repl = regex_match.group(0)[1:-1]
  9. start_span = regex_match.span()[0]
  10. end_span = regex_match.span()[1]
  11. for word in repl.split(self.SEPARATOR):
  12. tmpsentence = (
  13. sentence[0: start_span] +
  14. word +
  15. sentence[end_span:]
  16. )
  17. new_sentence = deepcopy(tmpsentence)
  18. self.combinations(new_sentence, master_sentence_list)

因此,master_sentence_list 变量像DFS树一样不断追加句子。

我想避免在同一句子中重复使用相同的单词 - 例如,如果我使用了单词“decline”,那么在递归调用后的内部for循环中选择下一组单词时不应再次使用它。是否有一种方法可以在解析第二个方括号模式中的单词时“存储”由第一个方括号内的单词使用的方式,以此类推?

就像DFS树,每个节点都必须存储其每个父节点的状态一样。

如何修改函数以在 sentence_list 中的单个句子中不再使用相同的单词?

我尝试使用一个名为 avoid_words: list 的参数来存储父节点单词的列表。但是,当我需要移动到第一个方括号中的下一个单词时(或者从不同的“根”开始时),如何擦除它?

英文:

I am using a recursive function to generate text using a RegEx match, where it finds a pattern of words according to a combination of synonyms inside square brackets (pattern = '\[.*?\]') separated by a string separator (I have defined a SEPARATOR =#lkmkmksdmf###. )

The initial sentence argument to the function is something like:

[decreasing#lkmkmksdmf###shrinking#lkmkmksdmf###falling#lkmkmksdmf###contracting#lkmkmksdmf###faltering#lkmkmksdmf###the contraction in] exports of services will drive national economy to a 0.3% real GDP [decline#lkmkmksdmf###decrease#lkmkmksdmf###contraction] in 2023 from an estimated 5.0% [decline#lkmkmksdmf###decrease#lkmkmksdmf###contraction] in 2022

and

The function reads like:

  1. def combinations(self,sentence,master_sentence_list:list):
  2. pattern = '\[.*?\]'
  3. if not re.findall(pattern, sentence, flags = re.IGNORECASE):
  4. if sentence not in sentence_list:
  5. sentence_list.append(sentence)
  6. else:
  7. for regex_match in re.finditer(pattern, sentence, flags = re.IGNORECASE):
  8. repl=regex_match.group(0)[1:-1]
  9. start_span = regex_match.span()[0]
  10. end_span = regex_match.span()[1]
  11. for word in repl.split(self.SEPARATOR):
  12. tmpsentence = (
  13. sentence[0: start_span] +
  14. word +
  15. sentence[end_span:]
  16. )
  17. new_sentence = deepcopy(tmpsentence)
  18. self.combinations(new_sentence,master_sentence_list)

Thus, the master_sentence_list variable keeps appending the sentences like a DFS tree

I want to avoid using the same words twice - for example if I used the word "decline" then it should not be used again while choosing the next set of words in the inner for loop after the recursive call. Is there a way of "storing" the word used by the words inside the first square bracket when a word from the second square brackets pattern is parsed and so on?

*It is like a DFS tree where each node has to store the state of each of its parent node.
*
How can I modify the function to not use the same words again in a single sentence of the sentence_list?

I tried using an argument called "avoid_words: list" to which would store the list of the parent node words. But how do I erase it when I have to move over to the next word in from the first square bracket (or starts from a different "root")?

答案1

得分: 3

Tim指出,如果确实没有其他输入字符串及其参数的方法(我对此表示怀疑),你应该使用split()函数将初始句子分成单词(同义词)和纯句子。

下面是我会使用的已注释代码,如果我不得不解决这种情况。

  1. def all_combinations(sentence) -> list:
  2. pattern = r'\[(.*?)\]'
  3. synonyms = []
  4. resulting_sentences = []
  5. # 将所有同义词放入同义词列表中
  6. list_of_synonyms = re.findall(pattern, sentence, flags=re.IGNORECASE)
  7. # 从原始句子中删除同义词
  8. sentence = re.sub(pattern, '[]', sentence)
  9. # 将同义词拆分为包含元组和时钟的字典
  10. for i, x in enumerate(list_of_synonyms):
  11. synonyms.append(tuple(x.split('#lkmkmksdmf###')))
  12. # 创建组合并将其放入集合列表中。
  13. # 集合只能容纳唯一的元素,因此在重复性的情况下,它们将更短。
  14. # 如果长度小于3,则将删除该集合。
  15. synonym_combinations = list(
  16. set(combinations) for combinations in itertools.product(*synonyms) if len(set(combinations)) == 3)
  17. # 遍历组合
  18. for combination in synonym_combinations:
  19. # 遍历组合中的单词
  20. formatted_sentence = sentence
  21. for synonym in combination:
  22. formatted_sentence = formatted_sentence.replace('[]', synonym, 1)
  23. # 将格式化后的句子添加到结果句子中
  24. resulting_sentences.append(formatted_sentence)
  25. return resulting_sentences
英文:

As Tim pointed out, if there really is no other way to input the string and it's arguments (which I doubt) you should use split() function to separate initial sentence into words (synonyms) and pure sentence.

Bellow is the commented code I would use, have I had to solve a situation like this.

  1. def all_combinations(sentence) -> list:
  2. pattern = r'\[(.*?)\]'
  3. synonyms = []
  4. resulting_sentences = []
  5. #Put all of the synonyms into synonyms list
  6. list_of_synonyms = re.findall(pattern, sentence, flags = re.IGNORECASE)
  7. #Remove synonyms from the origingal sentence
  8. sentence = re.sub(pattern, '[]', sentence)
  9. #split sinynonyms into dictionaries containing tuple and clock
  10. for i, x in enumerate(list_of_synonyms):
  11. synonyms.append(tuple(x.split('#lkmkmksdmf###')))
  12. #Create combinations and put those into list of sets.
  13. # Sets can hold only unique elements, thus in case of duplicity thwy will be shorter.
  14. # The set will be removed if it's length is <3.
  15. synonym_combinations = list(set(combinations) for combinations in itertools.product(*synonyms) if len(set(combinations)) == 3)
  16. #iterate over combinations
  17. for combination in synonym_combinations:
  18. #iterate over words in combinations
  19. formatted_sentence = sentence
  20. for synonym in combination: formatted_sentence = formatted_sentence.replace('[]',synonym,1)
  21. #append formatted sentence to resulting senteces
  22. resulting_sentences.append(formatted_sentence)
  23. return resulting_sentences

huangapple
  • 本文由 发表于 2023年7月28日 03:22:18
  • 转载请务必保留本文链接:https://go.coder-hub.com/76782819.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定