`
雄风铁骑
  • 浏览: 1892 次
  • 性别: Icon_minigender_1
  • 来自: 广州
最近访客 更多访客>>
文章分类
社区版块
存档分类
最新评论

最新IP地址数据库 二分逼近算法 高效解析800万大数据之区域分布

    博客分类:
  • c#
阅读更多

最新IP地址数据库  来自 qqzeng.com 

利用二分逼近法(bisection method) ,解析800多万IP 只需几十秒, 比较高效!

原来的顺序查找算法 效率比较低

C# code?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
 readonly string ipBinaryFilePath = "qqzengipdb.dat";
        readonly byte[] dataBuffer, indexBuffer;
        readonly uint[] index = new uint[256];
        readonly int dataLength;
        public IpLocation()
        {
            try
            {
                FileInfo file = new FileInfo(ipBinaryFilePath);
                dataBuffer = new byte[file.Length];
                using (var fin = new FileStream(file.FullName, FileMode.Open, FileAccess.Read))
                {
                    fin.Read(dataBuffer, 0, dataBuffer.Length);
                }                
                var offset_len = BytesToLong(dataBuffer[0], dataBuffer[1], dataBuffer[2], dataBuffer[3]); //Big Endian
                indexBuffer = new byte[offset_len];
                Array.Copy(dataBuffer, 4, indexBuffer, 0, offset_len);
                dataLength = (int)offset_len;
                for (int loop = 0; loop < 256; loop++)
                {
                    //索引 四字节  LITTLE_ENDIAN
                    index[loop] = BytesToLong(indexBuffer[loop * 4 + 3], indexBuffer[loop * 4 + 2], indexBuffer[loop * 4 + 1], indexBuffer[loop * 4]);
                }
            }
            catch { }
        }
 
        public string[] Find(string ip)
        {
            var ips = ip.Split('.');
            uint ip_prefix = uint.Parse(ips[0]);
            uint find_uint32 = BytesToLong(byte.Parse(ips[0]), byte.Parse(ips[1]), byte.Parse(ips[2]), byte.Parse(ips[3]));//BIG_ENDIAN
           
            // LITTLE_ENDIAN
            int max_len = 0;       
            int resultOffset =-1;
            int resultLegth =-1;
             
            uint start = index[ip_prefix] * 8 + 1024;
            if (ip_prefix != 255)
            {
                max_len = (int)index[ip_prefix + 1] * 8 + 1024;
            }
            else
            {
                max_len = (int)index[255] * 8 + 1024+1;
            }
    
            for (; start < max_len; start += 8)
            {
                // 前四位 结束ip   后三位 偏移  最后一位 内容长度 
                uint endipNum = BytesToLong(indexBuffer[start + 0], indexBuffer[start + 1], indexBuffer[start + 2], indexBuffer[start + 3]);//BIG_ENDIAN
                if (endipNum >= find_uint32)
                {
                    resultOffset =(int) BytesToLong((byte)0, indexBuffer[start + 6], indexBuffer[start + 5], indexBuffer[start + 4]);//LITTLE_ENDIAN
                    resultLegth = 0xFF & indexBuffer[start + 7];// 长度
                    break;
                }             
            }
            if (resultOffset==-1||resultLegth==-1)
            {
                return new string[] {"N/A"};
            }
            var areaBytes = new byte[resultLegth];
            Array.Copy(dataBuffer, dataLength + resultOffset - 1024, areaBytes, 0, resultLegth);
            return Encoding.UTF8.GetString(areaBytes).Split(' ');
        }
 
      
        private static uint BytesToLong(byte a, byte b, byte c, byte d)
        {
            
            return ((uint)a << 24) | ((uint)b << 16) | ((uint)c << 8) | (uint)d;
        }
 
 
        public static string long2IP(long longIP)
        {
            StringBuilder sb = new StringBuilder("");
            sb.Append(longIP >> 24);
            sb.Append(".");
            //将高8位置0,然后右移16为
 
            sb.Append((longIP & 0x00FFFFFF) >> 16);
            sb.Append(".");
 
            sb.Append((longIP & 0x0000FFFF) >> 8);
            sb.Append(".");
            sb.Append((longIP & 0x000000FF));
 
            return sb.ToString();
 
        }
  
    }




改进版 采用二分逼近 算法(类似二分查找,但又不同)  性能提升很大

C# code?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
 public string[] Find(string ip)
        {
            var ips = ip.Split('.');
            uint ip_prefix = uint.Parse(ips[0]);
            uint find_uint32 = BytesToLong(byte.Parse(ips[0]), byte.Parse(ips[1]), byte.Parse(ips[2]), byte.Parse(ips[3]));//BIG_ENDIAN
            uint max_len = 0;
            int resultOffset = -1;
            int resultLegth = -1;
            uint start = index[ip_prefix];
            if (ip_prefix != 255)
            {
                max_len = index[ip_prefix + 1];
            }
            else
            {
                max_len = index[255];
            }
            uint num = max_len - start;
            uint my_index = BinarySearch(start, max_len, find_uint32);
            start = my_index * 8 + 1024;
            resultOffset = (int)BytesToLong((byte)0, indexBuffer[start + 6], indexBuffer[start + 5], indexBuffer[start + 4]);//LITTLE_ENDIAN
            resultLegth = 0xFF & indexBuffer[start + 7];// 长度
 
            if (resultOffset == -1 || resultLegth == -1)
            {
                return new string[] { "N/A" };
            }
            var areaBytes = new byte[resultLegth];
            Array.Copy(dataBuffer, dataLength + resultOffset - 1024, areaBytes, 0, resultLegth);
            return Encoding.UTF8.GetString(areaBytes).Split(' ');
        }
 
 
 
        /// <summary>
        /// 二分逼近
        /// </summary>
        public uint BinarySearch(uint low, uint high, uint k)
        {
            uint M = 0;
            while (low <= high)
            {
                uint mid = (low + high) / 2;
                uint endipNum = GetStartIp(mid);
                if (endipNum >= k)
                {
                    M = mid; //mid有可能是解
                    high = mid - 1;
                }
                else
                    low = mid + 1;
            }
            return M;
        }



有了上面高效算法  解析出来800多万数据 也很快   再用一个简单的ling 统计一下即可

C# code?
1
2
3
  var cn_result= from r in list
                        group r by r.cn into g
                        select new { key = g.Key, cnt = g.Count() };


 800多万数据  统计组图  






微信



1
1
分享到:
评论

相关推荐

    最新IP地址数据库

    最新IP地址数据库 ,可以做各种数据开发的原始资源

    最新IP地址数据库-多语言解析以及导入数据库脚本

    最新IP地址数据库-多语言解析以及导入数据库脚本 IP数据库-用途: IP地址归属地查询-IP地理解析数据库 -可根据IP获取用户使用线路(电信、联通、移动、教育网、铁通、鹏博士、广电网等) -可根据IP查询到中国(内地...

    IP地址数据库

    包含全球IP地址数据。

    最新国内IP地址数据库精简版,仅保留省份和城市(SQL版)

    国内最新IP地址数据库,可导入MYSQL,SQL查询方法: 首先把ip地址转换为整型数值,PHP可使用ip2long函数, SQL语句如下: SELECT * FROM `ip2city` WHERE '{转换后的ip整型数值}' BETWEEN `start_ip` AND `end_ip` ...

    IP地址数据库(QQIP地址) 纯真IP地址数据库

    IP地址数据库(QQIP地址) 纯真IP地址数据库.rar,全国IP地址数据库文件,比较详细的。

    全世界最新IP地址数据库 2017年12月数据

    全世界最新IP地址数据库,2017年12月最新数据,可用于网站IP地址查询,无错漏无重复。

    IP地址数据库(iP138测试版_txt)

    iP数据库字段说明(从左到右): 1.起始iP iP地址的长整形格式 2.结束iP iP地址的长整形格式 3.起始iP 完整iP地址 4.结束iP 完整iP地址 5.国家 6.省 7.市 8.运营商名称 9.邮政编码 10.地区区号

    纯真IP数据库(可在线更新加入最新的IP地址)

    收集了包括中国电信、中国移动、中国联通、长城宽带、聚友宽带等 ISP 的最新准确 IP 地址数据。包括 最全的网吧数据。希望能够通过大家的共同努力打造一个没有未知数据,没有错误数据的QQ IP。IP数据库每 5天更新一...

    IP地址离线查询数据库(MySQL版)

    IP地址离线查询数据库(MySQL版)版本1,单条记录描述形式如下: 1 0.0.0.0 0.255.255.255 IANA CZ88.NET 该版本不包含INET_ATOI后的转化版本

    面试 大数据 算法解析

    1.提取出某日访问百度次数最多的那个IP 2.有一个1G大小的一个文件,里面每一行是一个词 3.给定a、b两个文件,各存放50亿个url,每个url各占64字节,内存限制是4G,让你找出a、b文件共同的url? 4.在2.5亿个整数中找出...

    2021年5月最新IP数据库共529330条,PHP解析类。

    基于最新2021年5月IP数据库,共529330条,并对中文乱码进行处理,使用简单方便,如果Thinkphp中使用请添加命名空间。 使用方法: $IP = new IpLocation('QQWry.dat'); $area = $IP-&gt;getlocation('113.108.182.52')...

    qq ip地址数据库

    qq ip地址数据库

    最全ip地址MYSQL数据库

    最新最全的Ip地址mysql数据库,附加使用说明文档,可用于查询Ip地址所在国家和城市

    2009年最新IP地址数据库

    2009最新IP地址数据库,36万条数据。 数据是目前最流行的、数据最全的ip数据, 收集了包括中国电信、中国网通、长城宽带、网通宽带、聚友宽带等 ISP 的最新准确 IP 地址数据。包括最全的网吧数据。

    ip数据库ip数据库ip数据库

    ip数据库ip数据库ip数据库ip数据库ip数据库ip数据库ip数据库ip数据库ip数据库

    2009最新IP地址数据库

    2009最新IP地址数据库。 数据是目前最流行的、数据最全的ip数据, 收集了包括中国电信、中国网通、长城宽带、网通宽带、聚友宽带等 ISP 的最新准确 IP 地址数据。包括最全的网吧数据。希望能够通过大家的共同努力...

    纯真IP地址数据库

    纯真IP地址数据库

    解析IP地址连接SQL数据库速度慢的原因

    本文分析了使用IP地址连接SQL Server数据库的速度慢的原因,介绍了获取最新的Microsoft SQL Server 2000 Service Pack、最新的Microsoft Data Access Components 2.6 Service Pack来解决此问题。

    打造Mysql最新版的IP地址数据库-将纯真IP数据库导入Mysql

    打造Mysql最新版的IP地址数据库-将纯真IP数据库导入Mysql 1.到纯真网络下载最新的QQ IP数据库并安装。 2.运行“纯真IP地址数据库”,点击“解压”按钮,可以把数据库保存为文本格式,输入文件名保存:ip.txt。(当然...

Global site tag (gtag.js) - Google Analytics