I need to convert a python string which represents a dict into a python dict. The string might contain any valid dict representation, including windows style pathes (with backslashes), eg
mystring = u'{"baselocaldir":"c:\\tmp\\SrcTmp\\RepManager"}'
I would need a generic str to dict convert function, so this is just an example of a source string, which doesn't work. The source string might come from external sources. A python 2/3 compatible solution would be preferred.
I already tried the given answers:
json.loads does not work (even if I reformat the string to json syntax): raises exception
ast.literal_eval does not work: in this example it places a tab character in the result
eval: the same result as ast.literal_eval
I would put a hack on the string to replace 'c:' as a raw string literal r'c:'
mystring = u'{"baselocaldir": "c:\\tmp\\SrcTmp\\RepManager"}'.replace('"c:', 'r"c:')
_dict = eval(mystring)
_dict
Result:
{'baselocaldir': 'c:\\tmp\\SrcTmp\\RepManager'}
Edit3: after op change the sample string to double backslash, it is easier and no need to use regex:
mystring = u'{"baselocaldir":"c:\\tmp\\SrcTmp\\RepManager"}'
test = repr(mystring)[1:-1]
print(test)
# convert to dictionary
my_dict = json.loads(test)
print('dict key "baselocaldir" = ', my_dict["baselocaldir"])
output:
{"baselocaldir":"c:\\tmp\\SrcTmp\\RepManager"}
dict key "baselocaldir" = c:\tmp\SrcTmp\RepManager
Edit2: apparently using repr() alone is not enough, that's why i edited my answer to use regex and replace all the \\
to \\\\
, here is the code:
import re, json
mystring = u'{"baselocaldir":"c:\tmp\SrcTmp\RepManager"}'
test = re.sub(r'(?<=[^\\])\\(?=[^\\])', r'\\\\', repr(mystring)[1:-1])
print(test)
# convert to dictionary
my_dict = json.loads(test)
print('dict key "baselocaldir" = ', my_dict["baselocaldir"])
output:
{"baselocaldir":"c:\\tmp\\SrcTmp\\RepManager"}
dict key "baselocaldir" = c:\tmp\SrcTmp\RepManager
previous answer, which is not enough Edit: simple way to convert a string to raw is to use repr()
or "%r"
Here is a one step solution, credits goes to Nishanth Amuluru and Jed Alexander 9 years ago:
mystring = u'{"baselocaldir":"c:\tmp\SrcTmp\RepManager"}'
raw_str = "%r"%mystring
rep_str= repr(mystring)
print('original string = ', mystring)
print('Raw string = ', raw_str)
print('rep string = ', rep_str)
output:
original string = {"baselocaldir":"c: mp\SrcTmp\RepManager"}
Raw string = '{"baselocaldir":"c:\tmp\\SrcTmp\\RepManager"}'
rep string = '{"baselocaldir":"c:\tmp\\SrcTmp\\RepManager"}'
My (maybe not most elegant) solution:
But it works on python2 , python3 and with unicode chars in unicode strings:
text_type = None
if PY2:
string_types = basestring
text_type = unicode
else:
string_types = text_type = str
def DictUnescaceBackslash(oDict):
for key, value in iteritems(oDict):
if isinstance(value, dict):
DictUnescaceBackslash(value)
elif isinstance(value, string_types):
oDict[key]=oDict[key].replace("***BaCkSlAsH***","\\")
elif isinstance(value, list):
for elem in value:
DictUnescaceBackslash(elem)
mystring = u'{"baselocaldir":"c:\\tmp\\SrcTmp\\RepManager"}'
uString2 = mystring.replace("\\","***BaCkSlAsH***")
dDict = ast.literal_eval(uString2)
DictUnescaceBackslash(dDict)
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.