UDP是无连接的不可靠的传输协议,可以用在可靠传输不是很重要的情况下使用。
QUdpSocket是QAbstractSocket 的子类,它们都继承了QIODevice。所以可以用QUdpSocket进行发送接收数据。它和QTcpSocket最大的区别也就是,发送数据之前不需要建立连接。
以下简单例子,演示了用QUdpSocket如何实现客户端和服务端的通信。
服务端代码:
[cpp] view plain copy 1. class UDPServer:public QObject 2. { 3. Q_OBJECT 4. public: 5. UDPServer(QObject *parent = NULL); 6. ~UDPServer(); 7. private slots: 8. void readPendingDatagrams(); 9. private: 10. QUdpSocket *udpSocket; 11. 12. }; [cpp] view plain copy 1. UDPServer::UDPServer(QObject *parent /* = NULL */):QObject(parent) 2. { 3. udpSocket = new QUdpSocket(this); 4. udpSocket->bind(QHostAddress::LocalHost, 7755); 5. cout<<"Server is Running......"<<endl; 6. connect(udpSocket, SIGNAL(readyRead()),this, SLOT(readPendingDatagrams())); 7. } 8. 9. UDPServer::~UDPServer() 10. { 11. 12. } 13. 14. void UDPServer::readPendingDatagrams() 15. { 16. QHostAddress sender; 17. quint16 senderPort; 18. while (udpSocket->hasPendingDatagrams()) 19. { 20. QByteArray datagram; 21. datagram.resize(udpSocket->pendingDatagramSize()); 22. udpSocket->readDatagram(datagram.data(), datagram.size(),&sender, &senderPort); 23. string strMes(datagram); 24. std::cout<<strMes<<endl; 25. } 26. QString text = "hello ..."; 27. QByteArray datagram = text.toLocal8Bit(); 28. udpSocket->writeDatagram(datagram.data(),datagram.size(),sender, senderPort); 29. } 说明: 1. 我都是在自己的机器上测试,所以服务器地址都是localHost。即 [cpp] view plain copy udpSocket->bind(QHostAddress::LocalHost, 7755); 2. 给客户端回发信息 [cpp] view plain copy udpSocket->writeDatagram(datagram.data(),datagram.size(),sender, senderPort);
客户端代码:
[cpp] view plain copy 1. class UdpClient : public QWidget 2. { 3. Q_OBJECT 4. 5. public: 6. UdpClient(QWidget *parent = 0, Qt::WFlags flags = 0); 7. ~UdpClient(); 8. 9. private slots: 10. void sendMessageSlot(); 11. void readPendingDatagrams(); 12. private: 13. QUdpSocket *udpSocket; 14. QLineEdit *m_pLEdit; 15. QPushButton *m_pSendMesBtn; 16. QLabel *m_pMessage; 18. }; [cpp] view plain copy 1. UdpClient::UdpClient(QWidget *parent, Qt::WFlags flags) 2. : QWidget(parent, flags) 3. { 4. m_pLEdit = new QLineEdit(this); 5. m_pSendMesBtn = new QPushButton(tr("Sending"),this); 6. udpSocket = new QUdpSocket(this); 7. m_pMessage = new QLabel(this); 8. QHostAddress sender = udpSocket->localAddress(); 9. quint16 senderPort = udpSocket->localPort(); 10. udpSocket->bind(sender,senderPort); 11. m_pLEdit->setGeometry(5,5,100,20); 12. m_pSendMesBtn->setGeometry(110,5,50,20); 13. m_pMessage->setGeometry(5,30,150,20); 14. m_pLEdit->setStyleSheet("QLineEdit{color:red}"); 15. connect(m_pSendMesBtn, SIGNAL(clicked()),this, SLOT(sendMessageSlot())); 16. connect(udpSocket, SIGNAL(readyRead()),this, SLOT(readPendingDatagrams())); 19. 20. } 21. 22. UdpClient::~UdpClient() 23. { 24. 25. } 26. 27. void UdpClient::sendMessageSlot() 28. { 29. QString text = m_pLEdit->text(); 30. QByteArray datagram = text.toLocal8Bit(); 31. udpSocket->writeDatagram(datagram.data(),datagram.size(),QHostAddress::LocalHost, 7755); 32. } 33. 34. void UdpClient::readPendingDatagrams() 35. { 36. while (udpSocket->hasPendingDatagrams()) 37. { 38. QByteArray datagram; 39. datagram.resize(udpSocket->pendingDatagramSize()); 40. QHostAddress sender; 41. quint16 senderPort; 42. udpSocket->readDatagram(datagram.data(), datagram.size(),&sender, &senderPort); 43. QString text = QString(datagram); 44. m_pMessage->setText(text); 45. } 46. } 说明: 1. 绑定本地地址和端口,以接收客户端发过来的信息 [cpp] view plain copy a. QHostAddress sender = udpSocket->localAddress(); b. quint16 senderPort = udpSocket->localPort(); c. udpSocket->bind(sender,senderPort);