2

I am trying to load a configuration file into a dictionary with just one liner

The configuration file looks like this:

key1:
   nested-key1 = val1
   nested-key2 = val2

key2:
   nested-key3 = val3

The dictionary I'm trying to build should look like this:

 { key1:{nested-key1:val1, nested-key2:val2}, key2:{nested-key3:val3}}

By one liner I mean that I don't want to use a loop - just a fixed sequence of function calls (Number of key may vary).

something like:

f = open("/tmp/config")
dic = f.read().split("\n\n") ...
Ezra
  • 1,401
  • 5
  • 15
  • 33
  • 2
    And what's the rational behind "I don't want to use a loop" ? you understand that it means that you'll have to manually repeat the same command as many times as there are keys in the file? Do you know in advance the exact number of keys ? – Nir Alfasi Apr 21 '15 at 04:20
  • no. the number of keys is unknown. (question edited) – Ezra Apr 21 '15 at 04:21
  • so you can't do it without looping. – Nir Alfasi Apr 21 '15 at 04:24
  • @alfasin you can always replace a loop with recursive function calls – Konstantin Apr 21 '15 at 04:26
  • 1
    @Alik right, you can also cross the highway with a bucket on your head. The fact that you *can* do something doesn't mean that you *should* do it. (Especially when the OP don't provide a good reasoning for a silly restriction). – Nir Alfasi Apr 21 '15 at 04:28
  • It's not for production, I'm just playing and I felt that this is doable but I haven't succeeded to solve it myself. – Ezra Apr 21 '15 at 04:41
  • 1
    You realize of course that some kind of iteration/looping would still be required even if you don't explicitly use ``for`` or ``while``? As said in earlier comments you could do this recursively as this is a "parsing" problem. If I had more time I could replace all looping constructs one might use for a map/reduce style functional approach -- but you're just "hiding" the looping/iteration in something else. – James Mills Apr 21 '15 at 04:46
  • 1
    why don't use `json files`? with `json` package its very comfortable. – Zaaferani Apr 21 '15 at 04:47
  • Hiding the iteration could also be nice. I was hoping to do it with some text replacement and 'eval' but maybe I'm far off – Ezra Apr 21 '15 at 04:49
  • I don't think a single regular expression or search/replace could handle this in a generic way. – James Mills Apr 21 '15 at 04:50
  • @Zaaferani how would you do it with a json lib? – Ezra Apr 21 '15 at 04:52
  • @Ezra see: https://docs.python.org/2/library/json.html http://stackoverflow.com/questions/2835559/parsing-values-from-a-json-file-in-python – Zaaferani Apr 21 '15 at 04:58
  • This is what I've come up with having a play with [funcy](https://pypi.python.org/pypi/funcy) -- https://gist.github.com/prologic/9b31c053d1be2ebab8bd -- I'm sure some of this can be even further simplified and cleaned up; but it works (tm) :) – James Mills Apr 21 '15 at 05:51
  • 2
    Of course -- The syntax of this configuration file here is remarkably similar to YAML :) – James Mills Apr 21 '15 at 06:10

1 Answers1

3

Considering the similarity of the file format to the YAML format, I suggest you use a YAML parser:

import yaml

s = """
key1:
   nested-key1 = val1
   nested-key2 = val2

key2:
   nested-key3 = val3
"""

print yaml.load(s.replace("=", ":"))

The output is:

{'key2': 'nested-key3 , val3', 'key1': 'nested-key1 , val1 nested-key2 , val2'}

For reference:

moooeeeep
  • 31,622
  • 22
  • 98
  • 187
  • Great answer! Even if it doesn't directly answer the OP's question of a one-liner avoiding loops/iteration weird ways :) – James Mills Apr 21 '15 at 08:56