Python 合并/连接两个数据帧,一个具有IP地址,一个具有IP网络

Python 合并/连接两个数据帧,一个具有IP地址,一个具有IP网络,python,pandas,dataframe,ip-address,Python,Pandas,Dataframe,Ip Address,我有两个数据帧,一个包含IP地址(df_IP),一个包含IP网络(df_network)。 IP和网络的类型为ipaddress.IP\u address和ipaddress.IP\u network,可以检查IP是否位于网络中(IP in network) 数据帧如下所示: df_ip: IP 0 10.10.10.10 1 10.10.20.10 2 10.10.20.20 df_network: NETWORK NETWORK_NAME 0

我有两个数据帧,一个包含IP地址(
df_IP
),一个包含IP网络(
df_network
)。
IP和网络的类型为
ipaddress.IP\u address
ipaddress.IP\u network
,可以检查IP是否位于网络中(
IP in network

数据帧如下所示:

df_ip:
    IP
0   10.10.10.10
1   10.10.20.10
2   10.10.20.20

df_network:
    NETWORK         NETWORK_NAME
0   10.10.10.0/28   Subnet1
1   10.10.20.0/27   Subnet2
我想将
df_ip
df_network
合并/加入,添加每行ip所在的网络名称。

对于这个小实例,它应该返回以下内容:

df_merged:
    IP            NETWORK_NAME
0   10.10.10.10   Subnet1
1   10.10.20.10   Subnet2
2   10.10.20.20   Subnet2
我的实际数据帧要大得多,因此我不希望使用for循环来保持效率。
我如何才能最好地实现这一点?如果这需要更改数据类型,那没关系

注意:为了方便起见,我在下面添加了代码来创建数据

将熊猫作为pd导入
导入IP地址
#创建小型IP数据帧
values_ip=[ipaddress.ip_address('10.10.10.10'),
ip地址。ip地址('10.10.20.10'),
ip地址。ip地址('10.10.20.20')]
df_ip=pd.DataFrame()
df_ip['ip']=值
#创建小型网络数据帧
values_network=[ipaddress.ip_network('10.10.10.0/28'),
ip地址ip_网络('10.10.20.0/27')]
名称\u网络=['Subnet1',
'子网2']
df_network=pd.DataFrame()
df_网络['network']=值_网络
df_网络['network_NAME']=名称_网络

避免任何循环的有效方法是使用numpy数组检查where
ip&netmask==网络地址,这就是如何检查ip是否位于网络中

请注意,这只返回第一个匹配的网络名称

import numpy as np
net_masks = df_network.NETWORK.apply(lambda x: int(x.netmask)).to_numpy()
network_addresses = df_network.NETWORK.apply(lambda x: int(x.network_address)).to_numpy()

def get_first_network(ip):
    is_in_network = int(ip) & net_masks == network_addresses
    indices = np.argwhere(is_in_network)
    if indices.size>0:
        return df_network.loc[int(indices[0]), 'NETWORK_NAME' ]
    else:
        None

df_ip['network_name'] = df_ip.IP.apply(get_first_network)
其结果是:

            IP network_name
0  10.10.10.10      Subnet1
1  10.10.20.10      Subnet2
2  10.10.20.20      Subnet2