zoukankan      html  css  js  c++  java
  • 读取全球ip获取用户地区

    这个 首先说明下。ip库是qq纯真ip库 dat文件类型

      public static string QQipPath = AppDomain.CurrentDomain.BaseDirectory + "\ipdata\qqwry.dat";///QQ纯真ip库地址
    
    
           public static string GetCity(string IP)
            {
                string ipfilePath = QQipPath;
                IPSearch ipSearch = new IPSearch(ipfilePath);
                IPSearch.IPLocation loc = ipSearch.GetIPLocation(IP);
                return loc.country;
            }
    
    
      public class IPSearch
        {
            FileStream ipFile;
            long ip;
            string ipfilePath;
    
            ///<summary>
            /// 构造函数
            ///</summary>
            ///<param name="ipfilePath">纯真IP数据库路径</param>
            public IPSearch(string ipfilePath)
            {
                this.ipfilePath = ipfilePath;
            }
    
            ///<summary>
            /// 地理位置,包括国家和地区
            ///</summary>
            public struct IPLocation
            {
                public string country, area;
            }
            ///<summary>
            /// 获取指定IP所在地理位置
            ///</summary>
            ///<param name="strIP">要查询的IP地址</param>
            ///<returns></returns>
            public IPLocation GetIPLocation(string strIP)
            {
                ip = IPToLong(strIP);
                ipFile = new FileStream(ipfilePath, FileMode.Open, FileAccess.Read);
                long[] ipArray = BlockToArray(ReadIPBlock());
                long offset = SearchIP(ipArray, 0, ipArray.Length - 1) * 7 + 4;
                ipFile.Position += offset;//跳过起始IP
                ipFile.Position = ReadLongX(3) + 4;//跳过结束IP
    
                IPLocation loc = new IPLocation();
                int flag = ipFile.ReadByte();//读取标志
                if (flag == 1)//表示国家和地区被转向
                {
                    ipFile.Position = ReadLongX(3);
                    flag = ipFile.ReadByte();//再读标志
                }
                long countryOffset = ipFile.Position;
                loc.country = ReadString(flag);
    
                if (flag == 2)
                {
                    ipFile.Position = countryOffset + 3;
                }
                flag = ipFile.ReadByte();
                loc.area = ReadString(flag);
    
                ipFile.Close();
                ipFile = null;
                return loc;
            }
            ///<summary>
            /// 将字符串形式的IP转换位long
            ///</summary>
            ///<param name="strIP"></param>
            ///<returns></returns>
            public long IPToLong(string strIP)
            {
                byte[] ip_bytes = new byte[8];
                string[] strArr = strIP.Split(new char[] { '.' });
                if (strArr.Length - 1 >= 3)
                {
                    for (int i = 0; i < 4; i++)
                    {
                        ip_bytes[i] = byte.Parse(strArr[3 - i]);
                    }
                }
                return BitConverter.ToInt64(ip_bytes, 0);
            }
            ///<summary>
            /// 将索引区字节块中的起始IP转换成Long数组
            ///</summary>
            ///<param name="ipBlock"></param>
            long[] BlockToArray(byte[] ipBlock)
            {
                long[] ipArray = new long[ipBlock.Length / 7];
                int ipIndex = 0;
                byte[] temp = new byte[8];
                for (int i = 0; i < ipBlock.Length; i += 7)
                {
                    Array.Copy(ipBlock, i, temp, 0, 4);
                    ipArray[ipIndex] = BitConverter.ToInt64(temp, 0);
                    ipIndex++;
                }
                return ipArray;
            }
            ///<summary>
            /// 从IP数组中搜索指定IP并返回其索引
            ///</summary>
            ///<param name="ipArray">IP数组</param>
            ///<param name="start">指定搜索的起始位置</param>
            ///<param name="end">指定搜索的结束位置</param>
            ///<returns></returns>
            int SearchIP(long[] ipArray, int start, int end)
            {
                int middle = (start + end) / 2;
                if (middle == start)
                    return middle;
                else if (ip < ipArray[middle])
                    return SearchIP(ipArray, start, middle);
                else
                    return SearchIP(ipArray, middle, end);
            }
            ///<summary>
            /// 读取IP文件中索引区块
            ///</summary>
            ///<returns></returns>
            byte[] ReadIPBlock()
            {
                long startPosition = ReadLongX(4);
                long endPosition = ReadLongX(4);
                long count = (endPosition - startPosition) / 7 + 1;//总记录数
                ipFile.Position = startPosition;
                byte[] ipBlock = new byte[count * 7];
                ipFile.Read(ipBlock, 0, ipBlock.Length);
                ipFile.Position = startPosition;
                return ipBlock;
            }
            ///<summary>
            /// 从IP文件中读取指定字节并转换位long
            ///</summary>
            ///<param name="bytesCount">需要转换的字节数,主意不要超过8字节</param>
            ///<returns></returns>
            long ReadLongX(int bytesCount)
            {
                byte[] _bytes = new byte[8];
                ipFile.Read(_bytes, 0, bytesCount);
                return BitConverter.ToInt64(_bytes, 0);
            }
            ///<summary>
            /// 从IP文件中读取字符串
            ///</summary>
            ///<param name="flag">转向标志</param>
            ///<returns></returns>
            string ReadString(int flag)
            {
                if (flag == 1 || flag == 2)//转向标志
                    ipFile.Position = ReadLongX(3);
                else
                    ipFile.Position -= 1;
    
                List<byte> list = new List<byte>();
                byte b = (byte)ipFile.ReadByte();
                while (b > 0)
                {
                    list.Add(b);
                    b = (byte)ipFile.ReadByte();
                }
                return Encoding.Default.GetString(list.ToArray());
            }
    
            public string GetUserIp()
            {
                string ip;
                bool isErr = false;
                if (System.Web.HttpContext.Current.Request.ServerVariables["HTTP_X_ForWARDED_For"] == null)
                    ip = System.Web.HttpContext.Current.Request.ServerVariables["REMOTE_ADDR"].ToString();
                else
                    ip = System.Web.HttpContext.Current.Request.ServerVariables["HTTP_X_ForWARDED_For"].ToString();
                if (ip.Length > 15)
                {
                    if (ip.Contains(","))
                    {
                        ip = ip.Split(',')[0];
                        isErr = IsError(ip);
                    }
                    else
                    {
                        isErr = true;
                    }
                }
                else
                {
                    isErr = IsError(ip);
                }
                if (isErr)
                    return "1.1.1.1";
                else
                    return ip;
            }
            /// <summary>
            /// ip过滤
            /// </summary>
            /// <param name="ip"></param>
            /// <returns></returns>
            protected bool IsError(string ip)
            {
                string[] temp;
                bool isErr = false;
                temp = ip.Split('.');
                if (temp.Length == 4)
                {
                    for (int i = 0; i < temp.Length; i++)
                    {
                        if (temp[i].Length > 3) isErr = true;
                    }
                }
                else
                    isErr = true;
                return isErr;
            }
    
            public string GetIpAddress()
            {
                string result = String.Empty;
                result = HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"];
                if (result != null && result != String.Empty)
                {
                    //可能有代理     
                    if (result.IndexOf(".") == -1)    //没有"."肯定是非IPv4格式     
                        result = "1.1.1.1";
                    else
                    {
                        if (result.IndexOf(",") != -1)
                        {
                            //有",",估计多个代理。取第一个不是内网的IP。     
                            result = result.Replace(" ", "").Replace(""","");
                            string[] temparyip = result.Split(",;".ToCharArray());
                            for (int i = 0; i < temparyip.Length; i++)
                            {
                                if (!IsError(temparyip[i])
                                    && temparyip[i].Substring(0, 3) != "10."
                                    && temparyip[i].Substring(0, 7) != "192.168"
                                    && temparyip[i].Substring(0, 7) != "172.16.")
                                {
                                    return temparyip[i];    //找到不是内网的地址     
                                }
                            }
                        }
                        else if (!IsError(result)) //代理即是IP格式     
                            return result;
                        else
                            result = "1.1.1.1";   //代理中的内容 非IP,取IP     
                    }
                }
                string IpAddress = (HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"] != null && HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"] != String.Empty) ? HttpContext.Current.Request.ServerVariables["HTTP_X_FORWARDED_FOR"] : HttpContext.Current.Request.ServerVariables["REMOTE_ADDR"];
                if (null == result || result == String.Empty)
                    result = HttpContext.Current.Request.ServerVariables["REMOTE_ADDR"];
                if (result == null || result == String.Empty)
                    result = HttpContext.Current.Request.UserHostAddress;
                return result;
            }
        }
    
  • 相关阅读:
    ubuntu基本配置学习(1)
    UITabBarController使用详解
    Could not find a storyboard named 'Main' in bundle NSBundle </Users/tianxiao/
    检查更新功能
    SDWebImage手动清除缓存的方法
    错误记录1
    如何获取path路径
    iOS如何获得本地Documents下的文件夹名称或文件名称
    重头系统的学习,不会咱就学!2014.6.18
    错误1
  • 原文地址:https://www.cnblogs.com/huhaihua/p/4582521.html
Copyright © 2011-2022 走看看