4

I get a string like this

EXAMPLE{TEST;ANOTHER{PART1;PART2};UNLIMITED{POSSIBILITIES{LIKE;THIS}}}

and have to get a result like this

EXAMPLETEST
EXAMPLEANOTHERPART1
EXAMPLEANOTHERPART2
EXAMPLEUNLIMITEDPOSSIBILITIESLIKE
EXAMPLEUNLIMITEDPOSSIBILITIESTHIS

Because there could be a unlimited amount of nesting, I'm having troubles remembering the parts before. Could you maybe point me in the right direction ?

Thanks a lot

TheInovat
  • 65
  • 6
  • What are your rules? What is the order to read the string (from left to right? inside to outside?) What are the functions of {} and ;? – wong.lok.yin Mar 17 '20 at 09:15
  • @jasonwong Sorry if that wasn't clear. The left part of the opening bracket "{" is getting concatenated with every possibility inside the brackets. These options are divided with as semi-colon ";". Everything can be nested and there is no upper limit to it. As I result I want to get every possible concatenation. Hope that clears it up. – TheInovat Mar 17 '20 at 09:22
  • You somehow need to parse the brackets. This [Q&A](https://stackoverflow.com/questions/1651487/python-parsing-bracketed-blocks) might help. – AnsFourtyTwo Mar 17 '20 at 09:53

1 Answers1

5

Goal: Turn it into a dict. And then create your output from the dictionary.

>>> string = "EXAMPLE{TEST;ANOTHER{PART1;PART2};UNLIMITED{POSSIBILITIES{LIKE;THIS}}}"
>>> string = string.replace(";", ",").replace("{", ": {")
>>> string
'EXAMPLE: {TEST,ANOTHER: {PART1,PART2},UNLIMITED: {POSSIBILITIES: {LIKE,THIS}}}'

EXAMPLE, TEST, ANOTHER are strings but they aren't wrapped in quotation marks "" or ''.

Using RegEx to solve this problem:

>>> import re
>>> string = re.sub(r"(\w+)", r"'\1'", string)
>>> string
"'EXAMPLE': {'TEST','ANOTHER': {'PART1','PART2'},'UNLIMITED': {'POSSIBILITIES': {'LIKE','THIS'}}}"

This is still not a valid file format. It's not JSON. It's not a dict. It's a mixture of a dict and a set in Python.
Making it look more like a dictionary:

>>> string = re.sub(r"'(\w+)',", r"'\1': None, ", string)
>>> string = re.sub(r"'(\w+)'}", r"'\1': None}", string)
>>> string
"'EXAMPLE': {'TEST': None, 'ANOTHER': {'PART1': None, 'PART2': None},'UNLIMITED': {'POSSIBILITIES': {'LIKE': None, 'THIS': None}}}"

Now turning it into a Python object:

>>> my_dict = eval('{' + string + '}')
>>> my_dict
{'EXAMPLE': {'TEST': None, 'ANOTHER': {'PART1': None, 'PART2': None}, 'UNLIMITED': {'POSSIBILITIES': {'LIKE': None, 'THIS': None}}}}

Now you have a regular Python object which you can iterate through and do string manipulation. You can write a recursive function that concatenates your string:

>>> def create_output(dict_element, result):
...     if dict_element == None:
...         print(result)
...         return
...     for key, value in dict_element.items():
...         create_output(value, result + key)
...
>>> create_output(my_dict, "")
EXAMPLETEST
EXAMPLEANOTHERPART1
EXAMPLEANOTHERPART2
EXAMPLEUNLIMITEDPOSSIBILITIESLIKE
EXAMPLEUNLIMITEDPOSSIBILITIESTHIS
Tin Nguyen
  • 5,250
  • 1
  • 12
  • 32
  • Not the most straight forward thing to do, so I couldn't figure it out on my own. Had to change the regex a little for my needs but works perfectly now. Thanks ! – TheInovat Mar 17 '20 at 10:52
  • Be careful about my solution. This runs an `eval`. Against untrusted source it can be dangerous. Malicious people could inject their code here. Furthermore it does not check the original file format for conformity. This is something you can use to expand on. Glad I could help :-) – Tin Nguyen Mar 17 '20 at 10:53