Python-迭代列表和字典

Python-迭代列表和字典,python,list,Python,List,嗨,我在转载这个问题,但提供更多关于我试图实现的信息。在过去的几天里,它让我发疯,而我似乎无法取得进展。基本上,我有这样的数据结构: data_in =\ {'map': {'command_line': u'command goes here', 'scaninfo': {u'tcp': {'method': u'syn', 'services': u'80,443'}}, 'stats': {'downhosts': u'0',

嗨,我在转载这个问题,但提供更多关于我试图实现的信息。在过去的几天里,它让我发疯,而我似乎无法取得进展。基本上,我有这样的数据结构:

data_in =\
{'map': {'command_line': u'command goes here',
         'scaninfo': {u'tcp': {'method': u'syn', 'services': u'80,443'}},
         'stats': {'downhosts': u'0',
                   'elapsed': u'1.71',
                   'timestr': u'Thu Mar 20 18:18:09 2014',
                   'totalhosts': u'3',
                   'uphosts': u'3'}},
 'scan': {u'2a00:2384:0:208f::13': {'addresses': {u'ipv6': u'2a00:2384:0:f467::13',
                                                  u'mac': u'00:gf:88:9:56:D5'},
                                    'hostname': u'static.abc.com',
                                    'status': {'reason': u'nd-response',
                                               'state': u'up'},
                                    u'tcp': {80: {'conf': u'3',
                                                  'cpe': '',
                                                  'extrainfo': '',
                                                  'name': u'http',
                                                  'product': '',
                                                  'reason': u'syn-ack',
                                                  'state': u'open',
                                                  'version': ''},
                                             443: {'conf': u'3',
                                                   'cpe': '',
                                                   'extrainfo': '',
                                                   'name': u'https',
                                                   'product': '',
                                                   'reason': u'syn-ack',
                                                   'script': {u'ssl-cert': u'place holder'},
                                                   'state': u'open',
                                                   'version': ''}},
                                    'vendor': {u'00:0C:29:7C:13:D3': u'VMware'}},
          u'2a00:2384:0:208f::15': {'addresses': {u'ipv6': u'a848:2384:0:3456::15',
                                                  u'mac': u'00:gf:29:99:6D:96'},
                                    'hostname': u'static.xyz.com',
                                    'status': {'reason': u'nd-response',
                                               'state': u'up'},
                                    u'tcp': {80: {'conf': u'3',
                                                  'cpe': '',
                                                  'extrainfo': '',
                                                  'name': u'http',
                                                  'product': '',
                                                  'reason': u'syn-ack',
                                                  'state': u'open',
                                                  'version': ''},
                                             443: {'conf': u'3',
                                                   'cpe': '',
                                                   'extrainfo': '',
                                                   'name': u'https',
                                                   'product': '',
                                                   'reason': u'syn-ack',
                                                   'script': {u'ssl-cert': u'place holder'},
                                                   'state': u'open',
                                                   'version': ''}},
                                    'vendor': {u'00:0C:67:99:6f:96': u'VMware'}},
          u'2a00:2384:0:208f::16': {'addresses': {u'ipv6': u'8938:8584:0:8685::16',
                                                  u'mac': u'00:54:29:fg:55:0F'},
                                    'hostname': u'static.edf.com',
                                    'status': {'reason': u'nd-response',
                                               'state': u'up'},
                                    u'tcp': {80: {'conf': u'3',
                                                  'cpe': '',
                                                  'extrainfo': '',
                                                  'name': u'http',
                                                  'product': '',
                                                  'reason': u'syn-ack',
                                                  'state': u'open',
                                                  'version': ''},
                                             443: {'conf': u'3',
                                                   'cpe': '',
                                                   'extrainfo': '',
                                                   'name': u'https',
                                                   'product': '',
                                                   'reason': u'syn-ack',
                                                   'script': {u'ssl-cert': u'place holder'},
                                                   'state': u'open',
                                                   'version': ''}},
                                    'vendor': {u'00:0C:55:AE:33:ff': u'VMware'}}}}
需要创建一个简化版本,如下所示:

data_out =\
[{'address': u'2a00:2384:0:208f::13',
  'hostname': u'static.bt.com',
  'ports': [{80: {'reason': u'syn-ack', 'state': u'open'}},
            {443: {'reason': u'syn-ack',
                   'ssl_cert': u'place   holder',
                   'state': u'open'}}]}]
根据@jornsharpe之前的建议,我创建了一个帮助函数,使我能够找到键。事实证明,这很有帮助,但我仍在努力获得预期的结果

def find_key(data, search_key, out=None):
"""Find all values from a nested dictionary for a given key."""
if out is None:
    out = []
if isinstance(data, dict):
    if search_key in data:
        out.append(data[search_key])
    for key in data:
        find_key(data[key], search_key, out)
return out

这里的任何帮助都将不胜感激

这并不难;您只需仔细查看导致所需内容的数据结构—由于格式不当,这变得更加困难,因此我重新缩进了您的输入并标记了键(
很明显,你在上一个问题中接受的答案并没有那么有帮助。那么,你为什么不回去看看其他答案,这些答案更侧重于导航你的实际结构(而不是在任何地方随机查找键)试着自己想点什么?我认为你的数据输出格式不好。你用逗号代替冒号。应该是:
data_out=[{'address':u'2a00:2384:0:208f::13','hostname':u'static.bt.com','ports':[{80:{'state':u'open',reason':u'syn-ack'},{443:{'ssl_cert':u'placeholder','state':u'open','reason':u'syn-ack'}]}]
是的-很抱歉修复了它。谢谢!非常感谢-我花了这么长时间盯着它看,看不到树,撞到了一堵墙。正如你所说的,由于格式不好而变得更加困难。我将详细研究你的示例。再次感谢。
data_in = {
    'map': {
        'stats': {
            'uphosts': u'3',
            'timestr': u'Thu Mar 20 18:18:09 2014',
            'downhosts': u'0',
            'totalhosts': u'3',
            'elapsed': u'1.71'
        },
        'scaninfo': {
            u'tcp': {
                'services': u'80,443',
                'method': u'syn'
            }
        },
        'command_line': u'command goes here'
    },
    'scan': {                           # <==
        u'2a00:2384:0:208f::13': {          # <== !!!
            'status': {
                'state': u'up',
                'reason': u'nd-response'
            },
            'hostname': u'static.abc.com',      # !!!
            'vendor': {
                u'00:0C:29:7C:13:D3': u'VMware'
            },
            'addresses': {
                u'mac': u'00:gf:88:9:56:D5',
                u'ipv6': u'2a00:2384:0:f467::13'
            },
            u'tcp': {                       # <==
                80: {                       # <== !!!
                    'product': '',
                    'state': u'open',           # !!!
                    'version': '',
                    'name': u'http',
                    'conf': u'3',
                    'extrainfo': '',
                    'reason': u'syn-ack',       # !!!
                    'cpe': ''
                },
                443: {                      # <== !!!
                    'product': '',
                    'state': u'open',           # !!!
                    'version': '',
                    'name': u'https',
                    'conf': u'3',
                    'script': {             # <==
                        u'ssl-cert': u'place holder'  # !!!
                    },
                    'extrainfo': '',
                    'reason': u'syn-ack',       # !!!
                    'cpe': ''
                }
            }
        },
        u'2a00:2384:0:208f::15': {
            'status': {
                'state': u'up',
                'reason': u'nd-response'
            },
            'hostname': u'static.xyz.com',
            'vendor': {
                u'00:0C:67:99:6f:96': u'VMware'
            },
            'addresses': {
                u'mac': u'00:gf:29:99:6D:96',
                u'ipv6': u'a848:2384:0:3456::15'
            },
            u'tcp': {
                80: {
                    'product': '',
                    'state': u'open',
                    'version': '',
                    'name': u'http',
                    'conf': u'3',
                    'extrainfo': '',
                    'reason': u'syn-ack',
                    'cpe': ''
                },
                443: {
                    'product': '',
                    'state': u'open',
                    'version': '',
                    'name': u'https',
                    'conf': u'3',
                    'script': {
                        u'ssl-cert': u'place holder'
                    },
                    'extrainfo': '',
                    'reason': u'syn-ack',
                    'cpe': ''
                }
            }
        },
        u'2a00:2384:0:208f::16': {
            'status': {
                'state': u'up',
                'reason': u'nd-response'
            },
            'hostname': u'static.edf.com',
            'vendor': {
                u'00:0C:55:AE:33:ff': u'VMware'
            },
            'addresses': {
                u'mac': u'00:54:29:fg:55:0F',
                u'ipv6': u'8938:8584:0:8685::16'
            },
            u'tcp': {
                80: {
                    'product': '',
                    'state': u'open',
                    'version': '',
                    'name': u'http',
                    'conf': u'3',
                    'extrainfo': '',
                    'reason': u'syn-ack',
                    'cpe': ''
                },
                443: {
                    'product': '',
                    'state': u'open',
                    'version': '',
                    'name': u'https',
                    'conf': u'3',
                    'script': {
                        u'ssl-cert': u'place holder'
                    },
                    'extrainfo': '',
                    'reason': u'syn-ack',
                    'cpe': ''
                }
            }
        }
    }
}
data_out = [
    {
        'address': u'2a00:2384:0:208f::13',
        'hostname': u'static.bt.com',
        'ports': {
            80: {
                'state': u'open',
                'reason': u'syn-ack'
            },
            443: {
                'ssl_cert': u'place   holder',
                'state': u'open',
                'reason': u'syn-ack'
            }
        }
    }
]
def remap_port(port, port_data):
    result = {
        "state":  port_data["state"],
        "reason": port_data["reason"]
    }
    try:
        result["ssl_cert"] = port_data["script"]["ssl-cert"]
    except KeyError:
        pass
    return port, result

def remap_scanned_address(address, address_data):
    return {
        "address":  address,
        "hostname": address_data["hostname"],
        "ports":    dict(remap_port(port, port_data) for port,port_data in address_data["tcp"].items())
    }

def remap_scan_data(data_in):
    return [remap_scanned_address(address, address_data) for address, address_data in data_in["scan"].items()]

data_out = remap_scan_data(data_in)
[{'address': u'2a00:2384:0:208f::13',
  'hostname': u'static.abc.com',
  'ports': {80: {'reason': u'syn-ack', 'state': u'open'},
            443: {'reason': u'syn-ack',
                  'ssl_cert': u'place holder',
                  'state': u'open'}}},
 {'address': u'2a00:2384:0:208f::15',
  'hostname': u'static.xyz.com',
  'ports': {80: {'reason': u'syn-ack', 'state': u'open'},
            443: {'reason': u'syn-ack',
                  'ssl_cert': u'place holder',
                  'state': u'open'}}},
 {'address': u'2a00:2384:0:208f::16',
  'hostname': u'static.edf.com',
  'ports': {80: {'reason': u'syn-ack', 'state': u'open'},
            443: {'reason': u'syn-ack',
                  'ssl_cert': u'place holder',
                  'state': u'open'}}}]