C++ 如何检查Qt中的网络地址是否为本地

C++ 如何检查Qt中的网络地址是否为本地,c++,qt,C++,Qt,我想知道网络地址(名称或IP)是否指向远程服务器或本地计算机。我可以使用QHostInfo查找IP地址,但在这种情况下,我必须等待DNS服务器的响应。我不想知道服务器的IP地址,我只需要检查它是否是本地的。有没有更快的方法来检查这个 我可以使用QHostInfo查找IP地址,但在这种情况下,我必须等待DNS服务器的响应 QHostInfo使用特定于平台的名称解析机制。它可能根本不使用DNS。如果本地接口的主机名在hosts文件中,并且名称解析配置为使用它,则QHostInfo将以这种方式解析本地

我想知道网络地址(名称或IP)是否指向远程服务器或本地计算机。我可以使用
QHostInfo
查找IP地址,但在这种情况下,我必须等待DNS服务器的响应。我不想知道服务器的IP地址,我只需要检查它是否是本地的。有没有更快的方法来检查这个

我可以使用
QHostInfo
查找IP地址,但在这种情况下,我必须等待DNS服务器的响应

QHostInfo
使用特定于平台的名称解析机制。它可能根本不使用DNS。如果本地接口的主机名在hosts文件中,并且名称解析配置为使用它,则
QHostInfo
将以这种方式解析本地接口的地址。否则,如果平台配置为以这种方式解析名称,它将执行名称服务器查询

您最多只能检查
QHostAddress::isLoopback()
,然后检查它是否是
QNetworkInterface::alladdress()
中的一个

如果您的地址不是IP地址,并且不等于
QHostInfo::localHostName()
,则必须先使用
QHostInfo::lookupHost
获取一个地址。如果是主机文件中列出的本地接口名称或类似的本地解析机制,则会快速返回。您可以设置一个较短的超时(比如100ms),如果到那时还没有可用的查找结果,您可以假定它不是本地接口

下面是一个例子:

// https://github.com/KubaO/stackoverflown/tree/master/questions/host-lookup-36319049
#include <QtWidgets>
#include <QtNetwork>

class IfLookup : public QObject {
   Q_OBJECT
   int m_id;
   QTimer m_timer;
   void abort() {
      if (m_timer.isActive())
         QHostInfo::abortHostLookup(m_id);
      m_timer.stop();
   }
   Q_SLOT void lookupResult(const QHostInfo & host) {
      m_timer.stop();
      if (host.error() != QHostInfo::NoError)
         return hasResult(Error);
      for (auto ifAddr : QNetworkInterface::allAddresses())
         if (host.addresses().contains(ifAddr))
            return hasResult(Local);
      return hasResult(NonLocal);
   }
public:
   enum Result { Local, NonLocal, TimedOut, Error };
   IfLookup(QObject * parent = 0) : QObject(parent) {
      connect(&m_timer, &QTimer::timeout, this, [this]{
         abort();
         emit hasResult(TimedOut);
      });
   }
   Q_SIGNAL void hasResult(Result);
   Q_SLOT void lookup(QString name) {
      abort();
      name = name.trimmed().toUpper();
      QHostAddress addr(name);
      if (!addr.isNull()) {
         if (addr.isLoopback() || QNetworkInterface::allAddresses().contains(addr))
            return hasResult(Local);
         return hasResult(NonLocal);
      }
      if (QHostInfo::localHostName() == name)
         return hasResult(Local);
      m_id = QHostInfo::lookupHost(name, this, SLOT(lookupResult(QHostInfo)));
      m_timer.start(500);
   }
};

int main(int argc, char ** argv) {
   QApplication app{argc, argv};
   QWidget w;
   QFormLayout layout{&w};
   QLineEdit address;
   layout.addRow("Address to look up", &address);
   QLabel result;
   layout.addRow("Result", &result);
   QPushButton lookup{"Lookup"};
   layout.addRow(&lookup);
   lookup.setDefault(true);
   w.show();

   IfLookup ifLookup;
   QObject::connect(&lookup, &QPushButton::clicked, [&]{
      result.clear();
      ifLookup.lookup(address.text());
   });
   QObject::connect(&ifLookup, &IfLookup::hasResult, [&](IfLookup::Result r){
      static const QMap<IfLookup::Result, QString> msgs = {
         { IfLookup::Local, "Local" }, { IfLookup::NonLocal, "Non-Local" },
         { IfLookup::TimedOut, "Timed Out" }, { IfLookup::Error, "Lookup Error" }
      };
      result.setText(msgs.value(r));
   });

   return app.exec();
}

#include "main.moc"
//https://github.com/KubaO/stackoverflown/tree/master/questions/host-lookup-36319049
#包括
#包括
Ifookup类:公共QoObject{
Q_对象
国际货币基金组织;
QTimer mu定时器;
无效中止(){
if(m_timer.isActive())
QHostInfo::abortHostLookup(m_id);
m_timer.stop();
}
Q_插槽无效查找结果(常量QHostInfo和主机){
m_timer.stop();
if(host.error()!=QHostInfo::NoError)
返回结果(错误);
对于(自动ifAddr:QNetworkInterface::allAddresses())
if(host.addresses()包含(ifAddr))
返回结果(本地);
返回结果(非本地);
}
公众:
枚举结果{Local,NonLocal,TimedOut,Error};
IfLookup(QObject*parent=0):QObject(parent){
连接(&m_timer,&QTimer::timeout,this,[this]{
中止();
发射hasResult(TimedOut);
});
}
Q_信号无效结果(结果);
Q_插槽无效查找(QString名称){
中止();
name=name.trimmed().toUpper();
QHostAddress地址(名称);
如果(!addr.isNull()){
if(addr.isLoopback()| | QNetworkInterface::allAddresses().contains(addr))
返回结果(本地);
返回结果(非本地);
}
如果(QHostInfo::localHostName()==名称)
返回结果(本地);
m_id=QHostInfo::lookupHost(名称、此、插槽(lookupResult(QHostInfo));
m_定时器启动(500);
}
};
int main(int argc,字符**argv){
QApplication app{argc,argv};
qw;
QFormLayout布局图{&w};
QLineEdit地址;
layout.addRow(“要查找的地址”、&Address);
QLabel结果;
layout.addRow(“结果”、&Result);
QPushButton查找{“查找”};
layout.addRow(查找(&lookup);
setDefault(true);
w、 show();
IfLookup IfLookup;
QObject::connect(&lookup,&QPushButton::clicked,[&]{
result.clear();
ifLookup.lookup(address.text());
});
QObject::connect(&ifLookup,&ifLookup::hasResult,[&](ifLookup::Result r){
静态常数QMap msgs={
{IfLookup::Local,“Local”},{IfLookup::NonLocal,“Non Local”},
{IfLookup::TimedOut,“超时”},{IfLookup::Error,“查找错误”}
};
result.setText(msgs.value(r));
});
返回app.exec();
}
#包括“main.moc”

您的本地地址是什么?我想知道该地址是环回地址、别名(如localhost)还是指向本地计算机的全局IP地址。