Reputation: 170
I'm doing a relatively big project for my final thesis and therefore I am using a .ini file for storing and retrieving settings. However, I am unable to find an elegant solution for how to convert the strings (well, actually the strings inside the dictionary) that Configparser returns to numbers (ints and floats) and/or lists.
Googling the issue, I came across this SO thread which only tackles the 'list' part of my problem but using the top rated solution (defining lists inside the .ini file like that: list=item1,item2) didn't do anything for me, as the 'list' still shows up as a string after parsing. Also, I do not want to change format.
So I decided I would try it myself and came up with this solution:
import configparser
# create a new instance of a 'ConfigParser' class
config = configparser.ConfigParser()
# create mock-content for the config file
config["Test"] = {
"test_string":"string",
"test_int":"2",
"test_float":"3.0",
"test_list":"item1, item2"
}
# get the relevant settings
settings = config["Test"]
# pack the relevant settings into a dictionary
settings = dict(settings)
# iterate through all the key-value pairs and convert them, if possible
for key, value in settings.items():
# try to convert to int
try:
settings[key] = int(value)
# if the value can't be converted to int, it might be a float or a list
except ValueError:
# try converting it to a float
try:
settings[key] = float(value)
# if the value can't be converted to float, try converting to list
except ValueError:
if "," in value:
cont = value.split(",")
settings[key] = [item.strip() for item in cont]
else:
settings[key] = value
print(type(settings["test_string"]))
print(settings)
However, this seems so very inelegant and is so heavily nested and the task itself seems so important that I cannot believe that there is no "more official" solution to this that I am simply unable to find.
So, could please someone help me out here and tell me if there really is no better, more straightforward way to achieve this!?
Upvotes: 1
Views: 1099
Reputation: 8564
Best I can do is this (though it's kinda hacky and probably dangerous too):
for key, value in settings.items():
try: # will handle both ints and floats, even tuples with ints/floats
settings[key] = eval(value)
except NameError: # this means it's a string or a tuple with strings
get_val = list(map(str.strip, value.split(",")))
settings[key] = get_val if get_val[1:] else get_val[0]
This will work correctly for ints
, floats
as well as your comma separated values (it will evaluated it as a tuple, I guess that should be fine though I added a condition for that anyway).
Upvotes: 2