Inazuma
Inazuma

Reputation: 178

Read list from text file

I have been experimenting with ways of storing some variables from my python project in a user readable/editable text file. The text file is laid out like this:

a = "hello"
b = 123
c = [4,5,6]

As you can see, a is meant to be a string, b an integer, and c a list. The code I have so far goes as follows:

for line in file:
    name = line.split('=')[0]
    value = line.split('=')[1]
    vars()[name] = value

It splits the line at the '=' and sets the first section as the variable name, and the second section as the value for that variable.

However, when the program runs, instead of coming out as an integer and a list, b (123) and c ([4,5,6]) both are saved as strings.

Is there any way that I can convert the strings into their proper types? Or is their a better (but still simple) way of doing what I am trying to do?

Any help would be much appreciated. Thanks!

Upvotes: 0

Views: 162

Answers (3)

user3885927
user3885927

Reputation: 3503

"Or is their a better (but still simple) way of doing what I am trying to do?"

Option 1 One easy and good way is to use a dictionary in a python file just do an import.

myConfig.py

cfg={'a':"hello", 'b':123, 'c':[4,5,6]}

In your code:

from myConfig import *
print cfg['a']

You can also use indvidual variables instead of dictionary and do the same.

Option 2

If you don't want a python file you can read any other file and use exec to executing the command line by line. Docs here: https://docs.python.org/2/reference/simple_stmts.html#exec

You can use execfile but I believe it is discontinued in versoin 3.x Docs here: https://docs.python.org/2/library/functions.html#execfile

Option 3

You can also use other ways:

  1. Python ConfigParser: https://docs.python.org/2/library/configparser.html
  2. YAML files: http://pyyaml.org/wiki/PyYAMLDocumentation
  3. XML files: See this for an example: parsing XML configuration file using Etree in python

Upvotes: 4

m.wasowski
m.wasowski

Reputation: 6386

In addition to answers below, for simple data structures you can use json format and dictionaries or namedtuples:

import json
from ast import literal_eval
from collections import namedtuple

json_vars = """{
    'a' : "hello",
    'b' : 123,
    'c' : [4,5,6]
}"""


print json_vars
from_json = literal_eval(json_vars)
# or:
# from_json = json.loads(json_vars)

variables = namedtuple('Vars', from_json.keys())(*from_json.values())

print variables
print variables.a
print variables.b
print variables.c

print variables._asdict()
d = dict(variables._asdict())
print d

print d['a']
print d.items()


as_json_again = json.dumps(d, indent=2)

print as_json_again

For more advanced objects, see pickle module.

Upvotes: 0

Robᵩ
Robᵩ

Reputation: 168836

Here is one way, using ast.literal_eval:

import ast
def config_file(filename):
    result = {}
    with open(filename) as f:
        for line in f:
            line = line.split('=',1)
            result[line[0]] = ast.literal_eval(line[1].strip())
    return result

print config_file('cfg.txt')

You'll probably want more beef in the for loop, like ignoring blank lines, removing comments, etc.

Also note that this puts the data in a dict, and not into the vars() dict. You should keep data out of your variable names. If you do want to add your config variables to your namespace, you can still use my function like so:

vars().update(config_file('cfg.txt'))

Upvotes: 2

Related Questions