Is there a Python equivalent to Perl's Data::Dumper for inspecting data structures?
Is there a Python module that can be used in the same way as Perl's Data::Dumper
module?
Edit: Sorry, I should have been clearer. I was mainly after a module for inspecting data rather than persisting.
BTW Thanks for the answers. This is one awesom开发者_运维技巧e site!
Data::Dumper has two main uses: data persistence and debugging/inspecting objects. As far as I know, there isn't anything that's going to work exactly the same as Data::Dumper.
I use pickle for data persistence.
I use pprint to visually inspect my objects / debug.
I think the closest you will find is the pprint module.
>>> l = [1, 2, 3, 4]
>>> l.append(l)
>>> d = {1: l, 2: 'this is a string'}
>>> print d
{1: [1, 2, 3, 4, [...]], 2: 'this is a string'}
>>> pprint.pprint(d)
{1: [1, 2, 3, 4, <Recursion on list with id=47898714920216>],
2: 'this is a string'}
Possibly a couple of alternatives: pickle, marshal, shelve.
I too have been using Data::Dumper for quite some time and have gotten used to its way of displaying nicely formatted complex data structures. pprint as mentioned above does a pretty decent job, but I didn't quite like its formatting style. That plus pprint doesn't allow you to inspect objects like Data::Dumper does:
Searched on the net and came across these:
https://gist.github.com/1071857#file_dumper.pyamazon
>>> y = { 1: [1,2,3], 2: [{'a':1},{'b':2}]}
>>> pp = pprint.PrettyPrinter(indent = 4)
>>> pp.pprint(y)
{ 1: [1, 2, 3], 2: [{ 'a': 1}, { 'b': 2}]}
>>> print(Dumper.dump(y)) # Dumper is the python module in the above link
{ 1: [ 1 2 3 ] 2: [ { 'a': 1 } { 'b': 2 } ] }
>>> print(Dumper.dump(pp))
instance::pprint.PrettyPrinter __dict__ :: { '_depth': None '_stream': file:: > '_width': 80 '_indent_per_level': 4 }
Also worth checking is http://salmon-protocol.googlecode.com/svn-history/r24/trunk/salmon-playground/dumper.py It has its own style and seems useful too.
Here is a simple solution for dumping nested data made up of dictionaries, lists, or tuples (it works quite well for me):
Python2
def printStruct(struc, indent=0):
if isinstance(struc, dict):
print ' '*indent+'{'
for key,val in struc.iteritems():
if isinstance(val, (dict, list, tuple)):
print ' '*(indent+1) + str(key) + '=> '
printStruct(val, indent+2)
else:
print ' '*(indent+1) + str(key) + '=> ' + str(val)
print ' '*indent+'}'
elif isinstance(struc, list):
print ' '*indent + '['
for item in struc:
printStruct(item, indent+1)
print ' '*indent + ']'
elif isinstance(struc, tuple):
print ' '*indent + '('
for item in struc:
printStruct(item, indent+1)
print ' '*indent + ')'
else: print ' '*indent + str(struc)
Python3
def printStruct(struc, indent=0):
if isinstance(struc, dict):
print (' '*indent+'{')
for key,val in struc.items():
if isinstance(val, (dict, list, tuple)):
print (' '*(indent+1) + str(key) + '=> ')
printStruct(val, indent+2)
else:
print (' '*(indent+1) + str(key) + '=> ' + str(val))
print (' '*indent+'}')
elif isinstance(struc, list):
print (' '*indent + '[')
for item in struc:
printStruct(item, indent+1)
print (' '*indent + ']')
elif isinstance(struc, tuple):
print (' '*indent + '(')
for item in struc:
printStruct(item, indent+1)
print (' '*indent + ')')
else: print (' '*indent + str(struc))
See it at work:
>>> d = [{'a1':1, 'a2':2, 'a3':3}, [1,2,3], [{'b1':1, 'b2':2}, {'c1':1}], 'd1', 'd2', 'd3']
>>> printStruct(d)
[
{
a1=> 1
a3=> 3
a2=> 2
}
[
1
2
3
]
[
{
b1=> 1
b2=> 2
}
{
c1=> 1
}
]
d1
d2
d3
]
For serialization, there are many options.
One of the best is JSON, which is a language-agnostic standard for serialization. It is available in 2.6 in the stdlib
json
module and before that with the same API in the third-partysimplejson
module.You do not want to use
marshal
, which is fairly low-level. If you wanted what it provides, you would use pickle.I avoid using pickle the format is Python-only and insecure. Deserializing using pickle can execute arbitrary code.
- If you did use
pickle
, you want to use the C implementation thereof. (Doimport cPickle as pickle
.)
- If you did use
For debugging, you usually want to look at the object's
repr
or to use thepprint
module.
I needed to return Perl-like dump for API request so I came up with this which doesn't format the output to be pretty, but makes perfect job for me.
from decimal import Decimal
from datetime import datetime, date
def dump(self, obj):
if obj is None:
return "undef"
if isinstance(obj, dict):
return self.dump_dict(obj)
if isinstance(obj, (list, tuple)):
return self.dump_list(obj)
if isinstance(obj, Decimal):
return "'{:.05f}'".format(obj)
# ... or handle it your way
if isinstance(obj, (datetime, date)):
return "'{}'".format(obj.isoformat(
sep=' ',
timespec='milliseconds'))
# ... or handle it your way
return "'{}'".format(obj)
def dump_dict(self, obj):
result = []
for key, val in obj.items():
result.append(' => '.join((self.dump(key), self.dump(val))))
return ' '.join(('{', ', '.join(result), '}'))
def dump_list(self, obj):
result = []
for val in obj:
result.append(self.dump(val))
return ' '.join(('[', ', '.join(result), ']'))
Using the above:
example_dict = {'a': 'example1', 'b': 'example2', 'c': [1, 2, 3, 'asd'], 'd': [{'g': 'something1', 'e': 'something2'}, {'z': 'something1'}]}
print(dump(example_dict))
will ouput:
{ 'b' => 'example2', 'a' => 'example1', 'd' => [ { 'g' => 'something1', 'e' => 'something2' }, { 'z' => 'something1' } ], 'c' => [ '1', '2', '3', 'asd' ] }
If you want something that works better than pprint, but doesn't require rolling your own, try importing dumper from pypi:
https://github.com/jric/Dumper.py or
https://github.com/ericholscher/pypi/blob/master/dumper.py
Saw this and realized Python has something that works akin to Data::Dumper in Dumper. The author describes it as
Dump Python data structures (including class instances) in a nicely- nested, easy-to-read form. Handles recursive data structures properly, and has sensible options for limiting the extent of the dump both by simple depth and by some rules for how to handle contained instances.
Install it via pip. The Github repo is at https://github.com/jric/Dumper.py.
As far as inspecting your object goes, I found this a useful equivalent of Data:Dumper:
https://salmon-protocol.googlecode.com/svn-history/r24/trunk/salmon-playground/dumper.py
dumper.py archived from Google Code to Wayback Machine (archive.org)
or
dumper.py exported from Google Code to Github
It can handle unicode strings.
Isn't it true that all the answers ignore dumping anything else than a combination of the basic data types like lists, dicts, etc.? I have just ran pprint on an Python Xlib Window object and got… <<class 'Xlib.display.Window'> 0x004001fe>
… that's all. No data fields, no methods listed… Is there anything that does a real dump of an object? With e.g.: all its attributes?
精彩评论