C语言解析17monipdb.dat(http://www.ipip.net/)免费数据库

官方给的链接打不开,而且里面的逻辑,每次都会打开文件,所以自己做了点个修改,发上来,借大家参考:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <string>
#include <vector>
#include <fstream>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <assert.h>

class IP17MON {
public:
    static bool init(const std::string strPathToDataFile = "./17monipdb.dat") {
		if(is_init) {
			return true;
		}

        printf("Opening %s\n", strPathToDataFile.c_str());
        std::ifstream ifDataFile(strPathToDataFile.c_str(), std::ios::binary);
        if (ifDataFile.is_open() == false) {
            printf("%m\n");
            return false;
        }
        // std vector reserve
		vecDataFile.assign(std::istreambuf_iterator<char>(ifDataFile), std::istreambuf_iterator<char>());
        printf("Load %lu bytes success\n", vecDataFile.size());

        unsigned int uiIndexLen = 0;
        memcpy(&uiIndexLen, &vecDataFile[0], 4);
        uiIndexLen = ntohl(uiIndexLen);
        printf("uiIndexLen = %d\n", uiIndexLen);
        pIPIndex = &vecDataFile[4];
        pIPData = &vecDataFile[uiIndexLen];
		is_init = 1;
        return true;
    }

    static std::string find(const std::string strIP) {
        struct sockaddr_in stSockAddrInet;

		memset(&stSockAddrInet, 0, sizeof(struct sockaddr_in));
        if(inet_aton(strIP.c_str(), &stSockAddrInet.sin_addr) == 0) {
            printf("convert error\n");
            return "";
        }
        unsigned int uiIP = ntohl(stSockAddrInet.sin_addr.s_addr);

        // atoi The string can contain additional characters after those
        // that form the integral number, which are ignored and have no
        // effect on the behavior of this function.
        int iFirst = atoi(strIP.c_str());
        int iStart = 0;
        memcpy(&iStart, pIPIndex+(iFirst*4), 4);
		printf("iStart = %d\n", iStart);
        int iMaxComLen = pIPData - pIPIndex - 1024 - 4;

        int iIndexOffset = -1;
        unsigned char ucIndexLength = 0;
        for (iStart = iStart * 8 + 1024; iStart < iMaxComLen; iStart += 8) {
            unsigned int uiCurrIP = 0;
            memcpy(&uiCurrIP, pIPIndex+iStart, 4);
            uiCurrIP = ntohl(uiCurrIP);
            if (uiCurrIP >= uiIP) {
                iIndexOffset = 0;
                memcpy(&iIndexOffset, pIPIndex+iStart+4, 3);
                memcpy(&ucIndexLength, pIPIndex+iStart+7, 1);
                break;
            }
        }

        if (iIndexOffset == -1) {
            return "";
        }

        std::string strRegion(pIPData + iIndexOffset - 1024, ucIndexLength);
        return strRegion;
    }
public:
    static std::vector<char> vecDataFile;
    static char *pIPIndex, *pIPData;
	static int is_init;
};
char *IP17MON::pIPIndex;
char *IP17MON::pIPData;
int IP17MON::is_init = 0;
std::vector<char> IP17MON::vecDataFile;

extern "C" const char *find_monip(const char *ip)
{
    if (IP17MON::init() == false) {
		return "";
	}
    return IP17MON::find(ip).c_str();
}

  

时间: 2024-11-13 11:00:22

C语言解析17monipdb.dat(http://www.ipip.net/)免费数据库的相关文章

复习c语言解析教程(一)

       最近又去图书馆找学习c语言的书籍了,感觉   由 <美>Al Kelley和Ira Pohl   编著·麻志毅  译的<c语言解析教程>翻译本挺好,尤其是其中的c语言学习方法(当然我还是比较建议学过这两种语言之后再做浏览比较好),在学习c语言的过程中,穿插讲解了c++! 在c语言的道路上,自己还是要好好努力才是! 1.不包含头文件的程序也是可以运行的! int main() { int a=3,b=4; return 0; }   2.如果a和b是int类型的变量,其

C语言解析JSON源码

2020-01-09 关键字:cJSON.linux JSON解析 JSON 是一种在互联网领域内很常用的轻量级数据交换协议. 它与 XML 的地位差不多,但就笔者而言,笔者更喜欢 JSON 的风格,因为它更符合我们的思维习惯,同样一份数据,JSON 格式的就是比 XML 要清晰明了一些. 最近笔者需要在 C语言 上解析 JSON 格式,在网上一顿找,找到一份很不错的开源代码.经过一阵研究与修改以后,终于变成了让笔者用的很顺手的 C语言 版 JSON 解析器. 现将这份经笔者小小修改过的代码记录

使用go语言解析xml

操作系统: CentOS 6.9_x64 go语言版本: 1.8.3 问题描述 现有一个自动报障程序,如果服务出错会自动给指定人发送邮件,配置文件内容如下(default.xml): <?xml version="1.0" encoding="UTF-8"?> <config> <smtpServer>smtp.163.com</smtpServer> <smtpPort>25</smtpPort&g

看看如何用C语言解析LRC格式的歌词(上)

嗯,本该昨晚写的,结果因为系统出了点问题,所以便拖到了今天早上.好了,不废话了. 经常听歌的,必然都见过歌词吧.当然,我们这里要说的歌词格式是以LRC为后缀的歌词.此外,还有QRC,KRC格式的歌词.但相对来说,LRC格式歌词更为常见.我们先来看看LRC格式的歌词究竟长什么样: 好了,我们该怎么解读这种格式的歌词呢?推荐看百度百科对它的介绍,在此就不废话了. 相信写过音乐播放的或者想要写音乐播放器的都会涉及到歌词文件的解析吧.自然,使用高级语言可能更为方便一些.比如,我们可以用正则匹配的方式获得

看看如何用C语言解析LRC格式的歌词(下)

接上一篇,接下来将来看看怎么实现lyric.c文件. 嗯,在详细说明每个实现的函数之前,首先要在lyric.c中实现在头文件中声明的一些全局变量的定义.当然,要记得定义指针时应拴住指针到一个合法的位置处.因为一个未初始化的指针可能指向内存中任何一个位置,或许是个合法可访问的位置,又或许是个非法不可访问的位置.所以,为了安全起见,我们应当养成好习惯,即在指针初始化时指向一个确定的位置.具体定义如下: //initialize some global variables. char* lrc_tit

VBA中使用JavaScript脚本语言解析JSON数据

JSON:JavaScript 对象表示法(JavaScript Object Notation) 和xml相似,都是文本形式(保存在文本文件中或字符串等形式),比如: jsstr = {"系别":"历史系","班级":"一班", "学员":[ {"姓名":"张三","年龄":25,"性别":"男"}, {&

atitit.java解析sql语言解析器解释器的实现

1. 解析sql的本质:实现一个4gl dsl编程语言的编译器 1 2. 解析sql的基本的流程,词法分析,而后进行语法分析,语义分析,构建sql的AST 1 3. 词法分析器 2 4. 语法分析器--ANTLR 2 5. Eclipse插件,,ANTLR Studio 3 6. 一个基于javacc实现的解析器JSqlParser0.7(yr2011), 3 7. 样例代码-----解析sql表格列的名称and类型 3 8. }Sql的历史 4 9. 解析select语句 4 10. zql,

go语言解析网页利器goquery使用教程(爬虫必备)

某些时候需要爬取网页中指定信息时,通常需要一些框架解析网页行成dom模型,然后来操作节点来获取相应的信息.在java中很显然就是Jsoup,而在Golang里,应该就是这个goquery了吧. goquery github地址 https://github.com/PuerkitoBio/goquery 安装 由于它依赖 Go语言的 net/html 包以及css选择库 cascadia, 因此我们要先手动安装net/html包,后者不需要我们手动安装. 运行 go get https://gi

jetbrick-template模板语言解析数据

项目中,组装接口的请求报文和解析返回报文时,用到了模板语言jetbrick-template. 1. 请求报文拼装 如:需要拼装的请求报文格式如下: 那么在后台组装好对象后,可以通过模板取值从而拼接固定格式的报文 2. 响应报文解析 如:发送请求报文成功后,部分返回报文如下,需要对<response>节点下的数据进行解析 主要节点属性 这时需要配置解析模板 需要注意的是:返回报文<response>节点下主要节点属性共有6个,采用上面的解析模板,只有返回全部6个节点的信息时(即返回