使用 C# 和 WPF 获取 IP 地理位置

Posted

技术标签:

【中文标题】使用 C# 和 WPF 获取 IP 地理位置【英文标题】:Get IP geolocation using C# & WPF 【发布时间】:2013-11-21 09:41:09 【问题描述】:

我正在做一个模块,它可以使用我正在使用的设备的 IP 地址显示我的城市、州、纬度和经度。 但是,我无法正确处理。下面是我引用的另一个网站的代码:

internal GeoLoc GetMyGeoLocation()

    try
    
        //create a request to geoiptool.com
        var request = WebRequest.Create(new Uri("http://geoiptool.com/data.php")) as HttpWebRequest;


    if (request != null)
    
        //set the request user agent
        request.UserAgent = "Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.0; SLCC1; .NET CLR 2.0.50727)";

        //get the response
        using (var webResponse = (request.GetResponse() as HttpWebResponse))
            if (webResponse != null)
                using (var reader = new StreamReader(webResponse.GetResponseStream()))
                

                    //get the XML document
                    var doc = new XmlDocument();
                    doc.Load(reader);

                    //now we parse the XML document
                    var nodes = doc.GetElementsByTagName("marker");

                    Guard.AssertCondition(nodes.Count > 0,"nodes",new object());
                    //make sure we have nodes before looping
                    //if (nodes.Count > 0)
                    //
                        //grab the first response
                        var marker = nodes[0] as XmlElement;

                        Guard.AssertNotNull(marker, "marker");

                        //get the data and return it
                        _geoLoc.City = marker.GetAttribute("city");
                        _geoLoc.Country = marker.GetAttribute("country");
                        _geoLoc.Code = marker.GetAttribute("code");
                        _geoLoc.Host = marker.GetAttribute("host");
                        _geoLoc.Ip = marker.GetAttribute("ip");
                        _geoLoc.Latitude = marker.GetAttribute("lat");
                        _geoLoc.Lognitude = marker.GetAttribute("lng");
                        _geoLoc.State = GetMyState(_geoLoc.Latitude, _geoLoc.Lognitude);

                        return _geoLoc;
                    //
                
    

    // this code would only be reached if something went wrong 
    // no "marker" node perhaps?
    return new GeoLoc();

catch (Exception ex)

    throw;

所有代码都没有问题。唯一的问题是_geoLoc,它会在每个下方提示红线。这是什么意思?谢谢。

【问题讨论】:

变量_geoLoc是什么,在哪里初始化? 如果你用红线'_geoLoc',这意味着变量没有在你的类中声明或初始化。 【参考方案1】:

正如其他人所指出的,_geoLoc 没有定义。试试这样的

internal GeoLoc GetMyGeoLocation()

    try
    
        //create a request to geoiptool.com
        var request = WebRequest.Create(new Uri("http://geoiptool.com/data.php")) as HttpWebRequest;


    if (request != null)
    
        //set the request user agent
        request.UserAgent = "Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.0; SLCC1; .NET CLR 2.0.50727)";

        //get the response
        using (var webResponse = (request.GetResponse() as HttpWebResponse))
            if (webResponse != null)
                using (var reader = new StreamReader(webResponse.GetResponseStream()))
                

                    //get the XML document
                    var doc = new XmlDocument();
                    doc.Load(reader);

                    //now we parse the XML document
                    var nodes = doc.GetElementsByTagName("marker");

                    Guard.AssertCondition(nodes.Count > 0,"nodes",new object());
                    //make sure we have nodes before looping
                    //if (nodes.Count > 0)
                    //
                        //grab the first response
                        var marker = nodes[0] as XmlElement;

                        Guard.AssertNotNull(marker, "marker");

                        var _geoLoc = new GeoLoc();
                        //get the data and return it
                        _geoLoc.City = marker.GetAttribute("city");
                        _geoLoc.Country = marker.GetAttribute("country");
                        _geoLoc.Code = marker.GetAttribute("code");
                        _geoLoc.Host = marker.GetAttribute("host");
                        _geoLoc.Ip = marker.GetAttribute("ip");
                        _geoLoc.Latitude = marker.GetAttribute("lat");
                        _geoLoc.Lognitude = marker.GetAttribute("lng");
                        _geoLoc.State = GetMyState(_geoLoc.Latitude, _geoLoc.Lognitude);

                        return _geoLoc;
                    //
                
           

        // this code would only be reached if something went wrong 
        // no "marker" node perhaps?
        return new GeoLoc();
    
    catch (Exception ex)
    
        throw;
    

【讨论】:

感谢您的建议。它帮助很大。请问如何在 TextBlock 上显示结果? 获得方法调用的结果后,您可以将 TextBlock 的文本设置为使用 GeoLoc 对象的属性。 是 TextBlock.Text = _geoLoc.City.Value.ToString(); ? 如果这是你想看到的,试试看它是否有效。 GetAttribute 方法返回一个字符串,因此CityValue 属性可能不存在。我没有你所有的代码,我不知道你想要什么,所以我不能肯定地说这是否正确。 实际上我想在单击按钮后显示结果。所以我打算这样做: void onButtonClick(object sender, RoutedEventArgs e) try //以上所有代码 TextBlock.Text = _geoLoc.City; 有可能吗?【参考方案2】:

似乎你没有 instenciated _geoLoc 这应该在你使用它之前被 instenciatted。尝试类似的东西。

namespace MyNamespace

    public class GeoLoc
    
        public string City  get; set; 

        public string Country  get; set; 

        public string Code  get; set; 

        public string Host  get; set; 

        public string Ip  get; set; 

        public string Latitude  get; set; 

        public string Lognitude  get; set; 

        public object State  get; set; 
    
    public class TestGEO
    
        internal GeoLoc GetMyGeoLocation()
        
            GeoLoc _geoLoc = new GeoLoc();
            try
            
                //create a request to geoiptool.com
                var request = WebRequest.Create(new Uri("http://geoiptool.com/data.php")) as HttpWebRequest;


                if (request != null)
                
                    //set the request user agent
                    request.UserAgent = "Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.0; SLCC1; .NET CLR 2.0.50727)";

                    //get the response
                    using (var webResponse = (request.GetResponse() as HttpWebResponse))
                        if (webResponse != null)
                            using (var reader = new StreamReader(webResponse.GetResponseStream()))
                            

                                //get the XML document
                                var doc = new XmlDocument();
                                doc.Load(reader);

                                //now we parse the XML document
                                var nodes = doc.GetElementsByTagName("marker");

                                // Guard.AssertCondition(nodes.Count > 0, "nodes", new object());
                                //make sure we have nodes before looping
                                //if (nodes.Count > 0)
                                //
                                //grab the first response
                                var marker = nodes[0] as XmlElement;

                                //  Guard.AssertNotNull(marker, "marker");

                                //get the data and return it
                                _geoLoc.City = marker.GetAttribute("city");
                                _geoLoc.Country = marker.GetAttribute("country");
                                _geoLoc.Code = marker.GetAttribute("code");
                                _geoLoc.Host = marker.GetAttribute("host");
                                _geoLoc.Ip = marker.GetAttribute("ip");
                                _geoLoc.Latitude = marker.GetAttribute("lat");
                                _geoLoc.Lognitude = marker.GetAttribute("lng");
                                _geoLoc.State = GetMyState(_geoLoc.Latitude, _geoLoc.Lognitude);

                                return _geoLoc;
                                //
                            
                

                // this code would only be reached if something went wrong 
                // no "marker" node perhaps?
                return _geoLoc;
            
            catch (Exception ex)
            
                throw;
            
        

        private object GetMyState(string p, string p_2)
        
            ///do somting 
            return "State Name";
            //return you data;
        
    

【讨论】:

感谢您的建议。请问如何在 TextBlock 上显示我得到的结果? 覆盖 GeoLoc 类中的 ToString 方法,并将您想要显示为字符串的数据格式化。班级。或者您可以使用 geoloc.propertyname 来显示您想要显示的内容。 是 TextBlock.Text = _geoLoc.City.Value.ToString(); ? 类似于 TextBlock.Text = _geoLoc.City;

以上是关于使用 C# 和 WPF 获取 IP 地理位置的主要内容,如果未能解决你的问题,请参考以下文章

C#关于HttpClient的应用:获取IP所在的地理位置信息

(分享)根据IP获取地理位置(百度API)

为相同的前 16 位 IP 地址假设统一的地理 IP 分辨率是不是安全?

使用python根据ip获取目标地理位置信息

前端页面获取访问者的IP地址经纬度和地理位置

通过 IP 获取地理位置(Spigot 1.8 和 1.13.2)