在大型lis中查找对象之间的连接

2022-07-06 13:04:46 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个对象列表,这些对象是网络设备,因此它们具有诸如名称之类的属性和诸如连接的邻居之类的方法。我想找到所有相互连接的对象来创建链接对象。我正在做下面这样的事情,但结果是非常缓慢

for ref_device in iter(devices):
    for device in iter(devices):
        if ref_dev.name in device.connected_neighbor_devices():
            print ref_dev.name + ' <--> ' + device.name

更新: 我的数据基本上是一个网络设备对象列表。这些对象是由json生成的,json本身表示这些网络设备、它们的接口以及这些接口上的邻居。我有一个非常大的网络设备对象列表,每个对象都有几个接口。我想从这个列表中创建链接对象,其中一个链接对象将有两个通过任意数量的接口连接的网络设备对象(或者基本上是彼此的邻居)

我更新了我的代码如下

class Link(object):
    def __init__(self, dev_a, dev_b):
        self.dev_a = dev_a
        self.dev_b = dev_b
    def __repr__(self):
        return '{} - {}'.format(dev_a.name, dev_b.name)

links = []
names = {dev.name for dev in devices}
for ref_device in devices:
for neigh in ref_device.connected_neighbor_devices():
    if neigh in names:
        neigh_device = [d for d in devices if d.name == neigh][0]
        links.append(Link(ref_device, neigh_device))

Tags: 对象nameindevselfref列表forif链接deviceneigh网络设备devicesiter
1条回答
网友
1楼 ·

connected_neighbor_devices的结果中,双循环后跟成员资格测试似乎是不必要的,因为该方法本身似乎获得一系列连接的设备名称。你当然可以这样做:

names = {dev.name for dev in devices}

for ref_device in devices:
    for connected_name in ref_device.connected_neighbor_devices():
        if connected_name in names:
            print ref_device.name + ' < > ' + connected_name

初始set的创建和成员资格测试只是为了确保输出中不包括不属于devices集合的连接设备。这可能与现有代码的顺序不匹配,但可以根据需要进行更改;假设connected_neighbor_devices返回所连接设备的所有名称,这应该会得到您想要的结果,但是通过O(n)调用并扫描来自connected_neighbor_devices的结果,而不是O(n ** 2)。你知道吗