Question

Is there way I can capture the full structure of a pickle dictionary? If I have this pickle file:

{
    '9': {
        'Dual': {
            'spectrum' : ..., 
            'interferogram': ..., 
            'SNR': ...
         }, 
        'Top': {
            'spectrum' : ..., 
            'interferogram': ..., 
            'SNR': ...
         }, 
        'Bottom': {
            'spectrum' : ..., 
            'interferogram': ..., 
            'SNR': ...
         }
     }, 
     '10': ..., 
     '11': ...
}

What I want is a shortcut to look at all the keys in the pickle file without doing this:

lvl1 = dictionary.keys()
lvl2 = dictionary['9'].keys()
lvl3 = dictionary['9']['Dual'].keys()

As I will not know the keys inside the pickle file ahead of time, but I will know there are 3 levels.

I want to somehow get the different layers of the dictionary like this:

lvl1.keys() = {'9','10','11'}
lvl2.keys() = {'Dual', 'Top', 'Bottom'}
lvl3.keys() = {'spectrum', 'interferogram', 'SNR'}

Thanks!

Was it helpful?

Solution

If you are happy to assume the structure is the same all the way through, this has a natural recursive solution:

def layers(data):
    try:
        keys = [data.keys()]
    except ValueError:
        return
    rest = layers(next(iter(data.values())))
    return keys + rest if rest else keys

Or in 3.x:

from collections.abc import Mapping

def layers(data):
    if isinstance(data, Mapping):
        yield data.keys()
        yield from layers(next(data.values())) 

The advantage to this solution is that it doesn't rely on you knowing the number of layers.

[{'9','10','11'}, {'Dual', 'Top', 'Bottom'}, {'spectrum', 'interferogram', 'SNR'}]

OTHER TIPS

If the keys are uniform at each level (e.g. 9 has the same keys as 10, Dual has the same keys as Top), you could do something like this:

lvl1 = dictionary.keys()
lvl2 = dictionary[lvl1[0]].keys()
lvl3 = dictionary[lvl1[0]][lvl2[0]].keys()

This wouldn't assume prior knowledge of the actual key values.

Don't think there's a way to do this without traversing everything, but here's how you'd do that without too much code:

level_1_keys = [k1 for k1 in dictionary.keys()]
level_2_keys = []
level_3_keys = []
for v1 in dictionary.values():
    level_2_keys += [k2 for k2 in v1.keys()]
    for v2 in v.values():
        level_3_keys += [k3 for k3 in v2.keys()]

EDIT: Lattyware's recursive solution is pretty solid too and solves the problem more generally. You could do a general solution iteratively too with some fancy looping, but it would probably be overkill.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top