繁体   English   中英

如何使用collections.defaultdict以确保在Python中直接比较值

[英]How to use collections.defaultdict, to ensure a straightforward comparison of values in Python

基本上,这是对我在堆栈溢出中看到的上一个问题的代码修改,我发现进行端口扫描处理很有趣。 在这段代码中,我试图比较2个腌制文件,这些文件包含一个接一个执行的2个扫描的扫描结果。 我有兴趣寻找

端口组上的3个操作

 & (intersection): to see which ports have remained constant across scans (same ports) old - new: to see which ports were in the old scan but no longer in the new (deleted ports) new - old: to see which ports are in the new scan but were not in the old (added ports) 
def comp_ports(self,filename):
  try:
        f = open(filename)
        self.prev_report = pickle.load(f) # NmapReport

        for s in self.prev_report.hosts:
            self.old_port_dict[s.address] = collections.defaultdict(set())
            for x in s.get_open_ports():
                self.old_port_dict[s.address].add(x)

        for s in self.report.hosts:
            self.new_port_dict[s.address] = collections.defaultdict(set())
            for x in s.get_open_ports():
               self.new_port_dict[s.address].add(x)

        hosts = sorted(set(self.prev_report.hosts.keys() + self.report.hosts.keys()))

        for host in hosts:
                scan_same[host] = self.prev_report.hosts[host] & self.report.hosts[host]
                scan_new[host]  = self.report.hosts[host] - self.prev_report.hosts[host]
                scan_del[host]  = self.prev_report.hosts[host] - self.report.hosts[host]

        print()
        print('-' * 10, 'Same')
        for host, ports in scan_same.items():
            print(host, ':')
            for port in ports:
                 print(':::', port[0], '/', port[1])

        print()
        print('*' * 10, 'Added')
        for host, ports in scan_new.items():
            print(host, ':')
            for port in ports:
                  print(':::', port[0], '/', port[1])

        print()
        print('=' * 10, 'Deleted')
        for host, ports in scan_del.items():
            print(host, ':')
            for port in ports:
                   print(':::', port[0], '/', port[1])

  except Exception as l:
         print l

但是代码抛出:

first argument must be callable

帮助我有效地使用收藏集。

PS:尝试通过这种方式进行改进如何比较字典,看看有什么变化?

您需要传递一个可调用的(函数/类/方法),该可调用的函数将返回默认值,而不是默认值本身。

遵循表达式:

collections.defaultdict(set())

应替换为:

collections.defaultdict(set)

UPDATE

您需要在for循环之外创建defaultdict

self.old_port_dict = collections.defaultdict(set)
for s in self.prev_report.hosts:
    for x in s.get_open_ports():
        self.old_port_dict[s.address].add(x)

self.new_port_dict = collections.defaultdict(set)
for s in self.report.hosts:
    for x in s.get_open_ports():
        self.new_port_dict[s.address].add(x)

要回答标题中的问题,您需要做

collections.defaultdict(set)

您需要传递一些可以实例化的东西。 传入collections.defaultdict(set())传入实例化的东西。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM