判断ip是否在一个超大ip集中(识别国内ip)

2024-08-24 18:38

本文主要是介绍判断ip是否在一个超大ip集中(识别国内ip),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

原文地址: https://www.ikaze.cn/article/65

新需求需要通过ip展示不同语言,由于ip很多,因此字典并不适用,下面给出几个方法。

1. 通过ip位置数据库

比较有名的服务商有:ipip(付费), maxmind (付费),纯真 (免费)。

但在这个应用场景下,我们并不需要具体的位置信息,类似的方案会浪费不必要的内存因此放弃。

2. 利用ip的连续性

后面两个方法有个前提:ip地址列表中大部分是连续的。

这里我们已有了国内ip地址列表(已有开源的库,很好找,另外我用的这个库已经把ip合并为了CIDR格式的地址)。

我们先通过二进制把ip转为可直接比较的数字,再把连续的ip变为 (start_ip, end_ip) 这样的集合,就可以利用二分法快速查找了。

import ipcalcclass ChinaIp:def __init__(self):self.data = []def load(self, cidr_file='data/china_ip_list.txt'):with open(cidr_file, 'r')as f:for s in f.readlines():self.add(s.strip())def add(self, cidr):n = ipcalc.Network(cidr)self.data.append((n.host_first().ip, n.host_last().ip))def search(self, ip):l = 0r = len(self.data) - 1while l <= r:mid = (l + r) // 2if self.data[mid][0] <= ip <= self.data[mid][1]:return Trueelif self.data[mid][0] > ip:r = mid - 1elif self.data[mid][1] < ip:l = mid + 1else:return Falsereturn Falsedef __contains__(self, item):ip = ipcalc.IP(item).ipreturn self.search(ip)china_ip = ChinaIp()
china_ip.load()
print('223.70.163.83' in china_ip)

3. 利用CIDR的特性

CIDR 是形如 x.x.x.x/n 这样的地址,它表示一组网络地址相同的ip,其中n表示前n位作为网络地址。 

根据CIDR的特性,我们可以得到这样的结论:同一CIDR下的ip,其网络地址是相同的。 

因此我们可以把所有国内cidr地址的网络地址取出,放字典;对于一个ip,尝试可能的网络地址(即n),看其是否在字典中。

import ipcalcclass ChinaIp(object):def __init__(self):self.data = {}def load(self, cidr_files='data/china_ip_list.txt'):with open(cidr_files, 'r')as f:cidr_list = f.readlines()for cidr in cidr_list:self.insert(cidr.strip())def insert(self, cidr):network = ipcalc.Network(cidr)self.data[str(network.netmask())]=Truedef __contains__(self, ip):for i in range(1,33):netmask = str(ipcalc.Network(f'{ip}/{i}').netmask())if netmask in self.data:return Truereturn Falsechina_ip = ChinaIp()
china_ip.load()
print('223.70.163.83' in china_ip)

这个算法看起来没啥毛病,但实际测试中速度比第二种慢了很多,耗时的地方在比较时必须循环所有n,而二分法可以快速的排除不可能的部分。

对于这种情况,有两种优化方法:

1. 随机n的列表

class ChinaIp(object):...def __contains__(self, ip):l = list(range(1, 33))random.shuffle(l)for i in l:netmask = str(ipcalc.Network(f'{ip}/{i}').netmask())if netmask in self.data:return Truereturn False

这种方法在测试中,时间减少了一半多。

2. 排除不会出现的n

class ChinaIp(object):def __init__(self):...self.mask_set = set()...def insert(self, cidr):network = ipcalc.Network(cidr)self.data[str(network.netmask())] = Trueself.mask_set.add(network.mask)def __contains__(self, ip):for i in self.mask_set:netmask = str(ipcalc.Network(f'{ip}/{i}').netmask())if netmask in self.data:return Truereturn False

这样优化后速度和第二种持平,不过实际应用中还需要根据ip列表的情况来判断需要用哪种。

这篇关于判断ip是否在一个超大ip集中(识别国内ip)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!


原文地址:
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.chinasem.cn/article/1103290

相关文章

Python如何判断字符串中是否包含特殊字符并替换

《Python如何判断字符串中是否包含特殊字符并替换》这篇文章主要为大家详细介绍了如何使用Python实现判断字符串中是否包含特殊字符并使用空字符串替换掉,文中的示例代码讲解详细,感兴趣的小伙伴可以了... 目录python判断字符串中是否包含特殊字符方法一:使用正则表达式方法二:手动检查特定字符Pytho

Gradle在国内配置镜像加速的实现步骤

《Gradle在国内配置镜像加速的实现步骤》在国内使用Gradle构建项目时,最大的痛点就是依赖下载贼慢,甚至卡死,下面教你如何配置国内镜像加速Gradle下载依赖,主要是通过改写repositori... 目录引言一、修改 build.gradle 或 settings.gradle 的 reposito

使用Python和PaddleOCR实现图文识别的代码和步骤

《使用Python和PaddleOCR实现图文识别的代码和步骤》在当今数字化时代,图文识别技术的应用越来越广泛,如文档数字化、信息提取等,PaddleOCR是百度开源的一款强大的OCR工具包,它集成了... 目录一、引言二、环境准备2.1 安装 python2.2 安装 PaddlePaddle2.3 安装

Java根据IP地址实现归属地获取

《Java根据IP地址实现归属地获取》Ip2region是一个离线IP地址定位库和IP定位数据管理框架,这篇文章主要为大家详细介绍了Java如何使用Ip2region实现根据IP地址获取归属地,感兴趣... 目录一、使用Ip2region离线获取1、Ip2region简介2、导包3、下编程载xdb文件4、J

使用Python实现IP地址和端口状态检测与监控

《使用Python实现IP地址和端口状态检测与监控》在网络运维和服务器管理中,IP地址和端口的可用性监控是保障业务连续性的基础需求,本文将带你用Python从零打造一个高可用IP监控系统,感兴趣的小伙... 目录概述:为什么需要IP监控系统使用步骤说明1. 环境准备2. 系统部署3. 核心功能配置系统效果展

判断PyTorch是GPU版还是CPU版的方法小结

《判断PyTorch是GPU版还是CPU版的方法小结》PyTorch作为当前最流行的深度学习框架之一,支持在CPU和GPU(NVIDIACUDA)上运行,所以对于深度学习开发者来说,正确识别PyTor... 目录前言为什么需要区分GPU和CPU版本?性能差异硬件要求如何检查PyTorch版本?方法1:使用命

Go语言开发实现查询IP信息的MCP服务器

《Go语言开发实现查询IP信息的MCP服务器》随着MCP的快速普及和广泛应用,MCP服务器也层出不穷,本文将详细介绍如何在Go语言中使用go-mcp库来开发一个查询IP信息的MCP... 目录前言mcp-ip-geo 服务器目录结构说明查询 IP 信息功能实现工具实现工具管理查询单个 IP 信息工具的实现服

如何为Yarn配置国内源的详细教程

《如何为Yarn配置国内源的详细教程》在使用Yarn进行项目开发时,由于网络原因,直接使用官方源可能会导致下载速度慢或连接失败,配置国内源可以显著提高包的下载速度和稳定性,本文将详细介绍如何为Yarn... 目录一、查询当前使用的镜像源二、设置国内源1. 设置为淘宝镜像源2. 设置为其他国内源三、还原为官方

Python如何精准判断某个进程是否在运行

《Python如何精准判断某个进程是否在运行》这篇文章主要为大家详细介绍了Python如何精准判断某个进程是否在运行,本文为大家整理了3种方法并进行了对比,有需要的小伙伴可以跟随小编一起学习一下... 目录一、为什么需要判断进程是否存在二、方法1:用psutil库(推荐)三、方法2:用os.system调用

Maven的使用和配置国内源的保姆级教程

《Maven的使用和配置国内源的保姆级教程》Maven是⼀个项目管理工具,基于POM(ProjectObjectModel,项目对象模型)的概念,Maven可以通过一小段描述信息来管理项目的构建,报告... 目录1. 什么是Maven?2.创建⼀个Maven项目3.Maven 核心功能4.使用Maven H