Qt开发:QTcpSocket的详解

一、QTcpSocket 简介

  QTcpSocket 是 Qt 网络模块中用于实现基于 TCP 协议的客户端通信的类。它提供了一个面向流的接口,允许程序通过套接字连接到远程主机,发送和接收数据。

  • 所属模块:QtNetwork
  • 用于建立 TCP 客户端连接,读取/写入数据。
  • 特点:异步非阻塞(配合信号槽机制)、支持事件驱动编程模型。

二、常用方法的介绍和使用

2.1 void QTcpSocket::connectToHost(hostname, port)
用于发起 TCP 连接的核心函数,常用于客户端向服务器发起连接请求。

参数说明:
在这里插入图片描述
使用示例:

QTcpSocket* socket = new QTcpSocket(this);

// 连接信号槽
connect(socket, &QTcpSocket::connected, this, [](){
   
   
    qDebug() << "Connected to server.";
});
connect(socket, &QTcpSocket::errorOccurred, this, [](QAbstractSocket::SocketError err){
   
   
    qDebug() << "Connection error:" << err;
});

// 发起连接
socket->connectToHost("127.0.0.1", 12345);

阻塞等待连接:
如果在非 GUI 程序中使用,或者想同步等待连接结果,可以使用:

socket->connectToHost("127.0.0.1", 12345);
if (socket->waitForConnected(3000)) {
   
   
    qDebug() << "Connected!";
} else {
   
   
    qDebug() << "Connection failed:" << socket->errorString();
}

常见错误排查:
在这里插入图片描述
2.2 void QAbstractSocket::disconnectFromHost()
用于主动断开 TCP 连接的函数。它的作用是通知对方:客户端希望关闭连接,然后进行连接释放。

使用说明:
当调用 disconnectFromHost() 后:

  1. 客户端发送 TCP 的 FIN 包;
  2. 如果连接关闭成功,触发 disconnected() 信号;
  3. 如果对方已经关闭连接,你仍然可以调用它释放资源;
  4. 若要强制关闭连接,可以使用 abort()。

基本示例:

QTcpSocket* socket = new QTcpSocket(this);

// 建立连接
socket->connectToHost("127.0.0.1", 12345);
connect(socket, &QTcpSocket::connected, this, [socket]() {
   
   
    qDebug() << "Connected to server.";

    // 写入数据后断开
    socket->write("Bye Server!");
    socket->flush();  // 确保发送出去了
    socket->disconnectFromHost();
});

connect(socket, &QTcpSocket::disconnected, this, []() {
   
   
    qDebug() << "Disconnected from server.";
});

同步等待断开:

socket->disconnectFromHost();
if (socket->state() != QAbstractSocket::UnconnectedState) {
   
   
    socket->waitForDisconnected(3000);  // 最多等 3 秒
}

与 abort() 的区别:
在这里插入图片描述
建议:正常退出时用 disconnectFromHost();发生错误/异常时使用 abort() 立即关闭连接。

2.3 qint64 QIODevice::write(const char *data, qint64 maxSize)
它在客户端和服务端之间发送字节流,是实现 socket 通信的核心方法之一。

参数说明:

  • data:指向要发送的原始数据。
  • maxSize:要发送的数据长度(字节数)。

返回值:返回实际写入的字节数,如果返回 -1,表示写入失败。

注意事项:

  • write() 只将数据写入到内部缓冲区,并不保证立刻发送。
  • 若想确保数据被真正写出,可使用 flush() 或等待 bytesWritten(qint64) 信号。
  • 如果 socket 未连接,调用 write() 会失败。

示例代码:
示例 1:发送一个 C 风格字符串

QTcpSocket *socket = new QTcpSocket(this);
socket->connectToHost("127.0.0.1", 8888);

if (socket->waitForConnected(3000)) {
   
   
    const char *msg = "Hello from client!";
    qint64 bytesWritten = socket->write(msg, strlen(msg));
    qDebug() << "Bytes written:" << bytesWritten;
}

示例 2:发送结构体(二进制数据)

struct MyData {
   
   
    int id;
    float value;
    char name[16];
};

MyData data = {
   
   42, 3.14f, "example"};
qint64 size = sizeof(data);

QTcpSocket *socket = new QTcpSocket(this);
socket->connectToHost("127.0.0.1", 8888);

if (socket->waitForConnected(3000)) {
   
   
    qint64 bytesWritten 
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值