2017-02-25 27 views
1

python是否有办法从给定的起始网络地址获取下一个网络地址。使用ipaddress模块可以获得下一个主机IP,但有没有办法让自己的下一个网络?如何在python中给出起始网络地址的下一个网络地址

例如,如果我的起始网络地址是10.1.0.0/16,那么在每次迭代中,我想要获取下一个网络地址,如10.2.0.0/16,10.3.0.0/16等。

因此,在10.1.0.0/16的情况下,网络部分是前两个字节(10.1),其余部分是主机部分。我想单独的网络部分,在每个迭代递增,使主机部分,因为它是为如:

start_network = ipaddress.ip_network('10.1.0.0/16') 

# Now on each iteration I want the below output 

In [37]: next(start_network) 
Out[37]: IPv4Network('10.2.0.0/16') 
In [38]: next(start_network) 
Out[38]: IPv4Network('10.3.0.0/16') 

使用子网选择试过,但顾名思义它可以把你当前的网络中的子网

In [34]: network = ipaddress.ip_network('10.1.0.0/16') 

In [35]: network.subnets() 

但是我们的要求是获得下一个网络地址(最好是没有任何字符串操作)

+0

我已经发布了解决您的具体问题在这里:http://stackoverflow.com/a/42451377/7311767 –

+0

但你的答案是要得到下一个主机IP,而我的问题是让下一个网络地址 – Mohamed

+0

什么是下一个网络地址?如果我的答案不够,建议编辑你的问题,并用示例显示你的期望。 –

回答

2

图书馆ipcalc具有例程,使IP地址的数学很容易。

代码:

import ipcalc 
import itertools as it 

network = ipcalc.Network('10.1.0.0/16') 
network_addrs = (network + (i + 1) * network.size() for i in it.count()) 

测试代码:

print(next(network_addrs)) 
print(next(network_addrs)) 
print(next(network_addrs)) 

结果:

作为例子的迭代器获取下一个网络范围内的地址可以像做
10.2.0.0/16 
10.3.0.0/16 
10.4.0.0/16 

标准库只:

如果这将是最好不要安装ipcalc,从ipaddress.IPv4Network继承可以构造一个类。

import ipaddress 

class BetterIPv4Network(ipaddress.IPv4Network): 

    def __add__(self, offset): 
     """Add numeric offset to the IP.""" 
     new_base_addr = int(self.network_address) + offset 
     return self.__class__((new_base_addr, str(self.netmask))) 

    def size(self): 
     """Return network size.""" 
     start = int(self.network_address) 
     return int(self.broadcast_address) + 1 - start 

用法:

import itertools as it 

network = BetterIPv4Network(u'10.1.0.0/16') 
network_addrs = (network + (i + 1) * network.size() for i in it.count()) 

的Python 3.4:

的Python 3.4没有接受的元组来初始化ipaddress.IPv4Network。这段代码将解决这个问题。

class BetterIPv4Network(ipaddress.IPv4Network): 

    def __add__(self, offset): 
     """Add numeric offset to the IP.""" 
     new_base_addr = int(self.network_address) + offset 
     new_base_addr_str = str(self.__class__(new_base_addr)).split('/')[0] 
     return self.__class__(new_base_addr_str + '/' + str(self.netmask)) 

    def size(self): 
     """Return network size.""" 
     start = int(self.network_address) 
     return int(self.broadcast_address) + 1 - start 
+0

这也可以使用标准的python3模块(ipaddress)来实现吗? – Mohamed

+0

是的,这是可能的。 –

+0

这个解决方案是否依赖python版本?我看到python 3.4.1的一个问题。有没有解决办法?错误:AddressValueError:“(167903232,'255”在“(167903232,'255.255.0.0')”中允许的只有十进制数字“ – Mohamed