96-数据读写和文件管理-数据读写基本类-IO设备的基本接口类QIODevice

  • Post author:
  • Post category:其他




数据读写和文件管理

在程序运行时会生成各种各样的数据,如果数据量少,可以直接将其保存在内存中,算结束时清空内存并把结果保存到文件中;

如果在计算中生成大量的中间数据,则需要把数据写到临时文件中,计算结束时把临时文件删除。

为保存数据,可以用Python 提供的open()函数打开或新建文件进行文本文件的读写

对于大量的有固定格式的数据(例如用科学计数法表示的数据)可以用PySide6 提供的以数据流的方式读写文本数据二进制数据和原生数据的方法和函数,以及对临时文件进行管理和监控的函数,很方便地对数据进行读写和对文件进行管理。



数据读写基本类

把计算过程中的数据保存下来或者读取已有数据是任何程序都需要进行的工作PySide6 把文件当作输入输出设备,可以把数据写到设备中,或者从设备中读取数据,从而达到读写数据的目的。

可以利用QFile类调用QIODevice类的读写方法直接进行读写

或者把QFile类和QTextStream类结合起来用文本流(text stream)的方法进行文本数据的读写

还可以把 QFile类和QDataStream 类结合进来,用数据流(data stream)的方法进行二进制数据的读写。



IO设备的基本接口类QIODevice

QIODevice类是Qt中所有I/O设备的基本接口类。

QIODevice 类是抽象类,是执行读数据和写数据类(如 QFile QBuffer)的基类它提供读数据和写数据的接口。

from PySide6.QtCore import QIODevice

QIODevice(self)-> None
QIODevice(parent: PySide6.QtCore.QObject)-> None



QIODevice说明

QIODevicece为支持读取和写入数据块的设备(如QFile、QBuffer和QTcpSocket)提供了通用实现和抽象接口。QIODevices是抽象的,不能实例化,但通常使用它定义的接口来提供与设备无关的I/O功能。例如,Qt的XML类在QIODevices指针上操作,允许它们与各种设备(如文件和缓冲区)一起使用。

在访问设备之前,必须调用open()来设置正确的OpenMode(如ReadOnly或ReadWrite)。然后,您可以使用write()或putChar()对设备进行写入,并通过调用read()、readLine()或readAll()进行读取。使用完设备后,请调用close()。

QIODevices区分了两种类型的设备:随机访问设备和顺序设备。

  • 随机访问设备支持使用seek()查找任意位置。通过调用pos()可以获得文件中的当前位置。QFile和QBuffer是随机接入设备的示例。
  • 顺序设备不支持寻找任意位置。数据必须一次性读取。函数pos()和size()不适用于顺序设备。QTcpSocket和QProcess是顺序设备的例子。

您可以使用isSequential()来确定设备的类型。

当有新数据可供读取时,QIODevices会发出readyRead();例如,如果新的数据已经到达网络,或者如果额外的数据被附加到您正在读取的文件中。您可以调用bytesAvailable()来确定当前可供读取的字节数。在使用异步设备(如QTcpSocket)进行编程时,通常会将bytesAvailable()与readyRead()信号一起使用,其中数据片段可以在任意时间点到达。每当有效负载的数据被写入设备时,QIODevice都会发出bytesWritten()信号。使用bytesToWrite()来确定当前等待写入的数据量。

QIODevices的某些子类,如QTcpSocket和QProcess,是异步的。这意味着写()或读()等I/O函数总是立即返回,而当控制返回到事件循环时,可能会与设备本身进行通信。QIODevice提供的函数允许您强制立即执行这些操作,同时阻止调用线程并且不进入事件循环。这允许在没有事件循环的情况下或在单独的线程中使用QIODevices子类:

  • waitForReadyRead()-此函数暂停调用线程中的操作,直到有新的数据可供读取。
  • waitForBytesWritten()-此函数将挂起调用线程中的操作,直到将一个有效负载的数据写入设备。
  • 等待…。()-QIODevices的子类实现设备特定操作的阻塞功能。例如,QProcess有一个名为waitForStarted()的函数,它会挂起调用线程中的操作,直到进程启动为止。

从主GUI线程调用这些函数可能会导致用户界面冻结。例子:

gzip = QProcess()
gzip.start("gzip",QStringList()<<"-c")
if not gzip.waitForStarted():
    return False
gzip.write("uncompressed data")
compressed = QByteArray()
while gzip.waitForReadyRead():
    compressed += gzip.readAll()

通过子类化QIODevices,您可以为自己的I/O设备提供相同的接口。QIODevices的子类仅用于实现受保护的readData()和writeData()函数。QIODevice使用这些函数来实现其所有的便利函数,如getChar()、readLine()和write()。QIODevices还为您处理访问控制,因此如果调用writeData(),您可以安全地假设设备是以写模式打开的。

一些子类,如QFile和QTcpSocket,是使用用于数据中间存储的内存缓冲区来实现的。这减少了所需的设备访问呼叫的数量,而这些呼叫通常非常缓慢。缓冲使getChar()和putChar()等函数快速,因为它们可以在内存缓冲区上操作,而不是直接在设备本身上操作。然而,某些I/O操作在使用缓冲区时不能很好地工作。

例如,如果几个用户打开同一个设备并逐个字符地读取它,那么当他们打算分别读取一个单独的区块时,他们最终可能会读取相同的数据。因此,QIODevice允许您通过将Unbuffered标志传递给open()来绕过任何缓冲。在对QIODevicece进行子类化时,请记住在设备以Unbuffered模式打开时绕过可能使用的任何缓冲区。

通常,来自异步设备的传入数据流是分段的,数据块可以在任意时间点到达。要处理数据结构的不完整读取,请使用QIODevicece实现的事务机制。有关更多详细信息,请参阅startTransaction()和相关函数。

一些顺序设备支持通过多个通道进行通信。这些通道表示单独的数据流,具有独立排序传递的特性。打开设备后,您可以通过调用readChannelCount()和writeChannelCount[()函数来确定通道的数量。要在通道之间切换,请分别调用setCurrentReadChannel()和setCurrentWriteChannel()。

QIODevices还提供额外的信号来处理每个信道的异步通信。



QIODevice子类

类名 描述

QSerialPort
提供访问串行端口的功能。

QNetworkReply
QNetworkReply类包含使用QNetworkAccessManager发送的请求的数据和标头。

QLocalSocket
QLocalSocket类提供了一个本地套接字。

QAbstractSocket
QAbstractSocket类提供了所有套接字类型通用的基本功能。

QUdpSocket
QUdpSocket类提供了一个UDP套接字。

QTcpSocket
QTcpSocket类提供了一个TCP套接字。

QProcess
QProcess类用于启动外部程序并与它们进行通信。

QFileDevice
QFileDevice类提供了一个用于读取和写入打开文件的接口。

QSaveFile
QSaveFile类提供了一个用于安全写入文件的接口。

QFile
QFile类提供了一个用于读取和写入文件的接口。

QTemporaryFile
QTemporaryFile类是一个对临时文件进行操作的I/O设备。

QSslSocket
QSslSocket类为客户端和服务器提供SSL加密的套接字。

QBuffer
QBuffer类为QByteArray提供了一个QIODevice接口。

QCoapReply
QCoapReply类保存CoAP回复的数据。

QCoapResourceDiscoveryReply
QCoapResourceDiscoveryReply类保存资源发现请求的CoAP回复的数据。

QBluetoothSocket
QBluetoothSocket类允许连接到运行蓝牙服务器的蓝牙设备。

QIODevice类在 QtCore 模块中。直接或间接继承自 QIODevice,与本地读写文件有关的类有

  • QBuffer
  • QFile
  • QFileDevice
  • QProcess
  • QSaveFile
  • QTemporaryFile
from PySide6.QtCore import QBuffer,QFile,QFileDevice,QProcess,QSaveFile,QTemporaryFile

QBuffer(buf: Union[PySide6.QtCore.QByteArray,bytes],parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None
QBuffer(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None

QFile(self)-> None
QFile(name: Union[str,bytes,os.PathLike])-> None
QFile(name: Union[str,bytes,os.PathLike],parent: PySide6.QtCore.QObject)-> None
QFile(parent: PySide6.QtCore.QObject)-> None

QFileDevice(self)-> None
QFileDevice(parent: PySide6.QtCore.QObject)-> None

QProcess(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None

QSaveFile(name: str)-> None
QSaveFile(name: str,parent: PySide6.QtCore.QObject)-> None
QSaveFile(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None

QTemporaryFile(self)-> None
QTemporaryFile(parent: PySide6.QtCore.QObject)-> None
QTemporaryFile(templateName: str)-> None
QTemporaryFile(templateName: str,parent: PySide6.QtCore.QObject)-> None

这些类之间的继承关系如图所示。另外还有网络方面的读写类

  • QAbstractSocket
  • QLocalSocket
  • QNetworkReply
  • QSslSocket
  • QTcpSocket
  • QUdpSocket
from PySide6.QtNetwork import QAbstractSocket,QLocalSocket,QNetworkReply,QSslSocket,QTcpSocket,QUdpSocket

QAbstractSocket(socketType: PySide6.QtNetwork.QAbstractSocket.SocketType,parent: PySide6.QtCore.QObject)-> None\
QLocalSocket(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None
QNetworkReply(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None
QSslSocket(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None
QTcpSocket(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None
QUdpSocket(parent: Union[PySide6.QtCore.QObject,NoneType] = None)-> None

image-20230310133920454

QIODevice类提供读写接口但是不能直接使用QIODevice 类进行数据的读写而是使用子类QFile或QBuffer 的继承自QIODevice 的读写方法来进行数据读写。

在一些系统中将所有的外围设备都当作文件来处理,因此可以读写的类都可以当作设备来处理。



QIODevice方法

QIODevice的常用方法如表所示,主要方法介绍如下。

  • 读写设备分为两种,一种是随机设备(random-access device),另一种是顺序设备(sequential device),

    • 用isSequential()方法可以判断设备是否是顺序设备。

      • QFile和QBuffer 是随机设备
      • QTcpSocket 和QProcess 是顺序设备
    • 。随机设备可以获取设备指针的位置,将指针指向指定的位置,从指定位置读取数据;而顺序设备只能依次读取数据。

      • 随机设备可以用seek(pos:int)方法定位,
      • 用pos()方法获取位置
  • 读取数据的方法有

    • read(maxlen:int)、

    • readAll()、

    • readData(data: bytes,maxlen:int)、

    • readLine(maxlen: int=0)

    • readLineData(data: bytes,maxlen: int),

    • getChar(c:bytes)

    • peek(maxlen:int)

    • read(maxlen:int)表示读取指定长度的数据

      • readLine(maxlen:int=0)表示读取行参数maxlen 表示允许读取的最大长度,若为0表示不受限制。
  • 写人数据的方法有

    • write(QByteArray)

    • writeData(bytes)

    • putChar(c:str)

    • getChar(c;bytes)和 putChar(c;str)只能读取和写人一个字符

    • 如果要继承 QIODevice 创建自己的读写设备需要重写 readData()和 writeData()函数。

  • 一些顺序设备支持多通道读写,这些通道表示独立的数据流

    • 可以用setCurrentReadChannel(int)方法设置读取通道
    • 用setCurrentWriteChannel(int)方法设置写人通道
    • 用currentReadChannel()方法和currentWriteChannel()方法获取读取和写入通道
QIODevice的方法及参数类型 返回值的类型 说明
open(QIODeviceBase.OpenMode) bool 打开设备并将其”打开模式”设置为”OpenMode”。如果成功,则返回true;否则返回false。这个函数应该从打开设备的open()或其他函数的任何重新实现中调用。
isOpen() bool 如果设备处于打开状态,则返回true;否则返回false。如果可以读取和/或写入设备,则该设备处于打开状态。默认情况下,如果openMode()返回NotOpen,则此函数返回false。
setOpenMode(QIODeviceBase.OpenMode) None 将设备的OpenMode设置为OpenMode。如果设备打开后标志发生变化,则调用此函数设置打开模式。
openMode() OpenMode 返回设备打开的模式;即ReadOnly或WriteOnly。
close() None 首先发出aboutToClose(),然后关闭设备并将其OpenMode设置为NotOpen。错误字符串也会被重置。
setTextModeEnabled(bool) None 如果启用为true,此功能将设置设备上的Text标志;否则将删除文本标志。此功能对于在QIODevices上提供自定义行末处理的类非常有用。

在调用此函数之前,应先打开IO设备。
read(maxlen: int) PySide6.QtCore.QByteArray 这是一个重载函数。

从设备中最多读取maxSize字节,并将读取的数据作为QByteArray返回。

此功能无法报告错误;返回一个空的QByteArray可能意味着当前没有可供读取的数据,或者发生了错误。
readAll() PySide6.QtCore.QByteArray 从设备中读取所有剩余数据,并将其作为字节数组返回。

此功能无法报告错误;返回一个空的QByteArray可能意味着当前没有可供读取的数据,或者发生了错误。此函数也无法指示可能有更多数据可用且无法读取。
readLine(maxlen:int=0) QByteArray 这是一个重载函数。

从设备中读取一行,但不超过maxSize个字符,并以字节数组的形式返回结果。

此功能无法报告错误;返回一个空的QByteArray可能意味着当前没有可供读取的数据,或者发生了错误。
readData(maxlen:int) PyObject 从设备中读取最多maxSize字节的数据,并返回读取的字节数,如果发生错误,则返回-1。

如果没有要读取的字节,并且永远不会有更多的字节可用(例如,套接字关闭、管道关闭、子进程完成),则此函数返回-1。

此函数由QIODevice调用。在创建QIODevicece的子类时重新实现此函数。

当重新实现此函数时,重要的是此函数在返回之前读取所有必需的数据。这是QDataStream能够对类进行操作所必需的。QDataStream假定已读取所有请求的信息,因此如果出现问题,则不会重试读取。

调用此函数时,maxSize可能为0,可用于执行读取后操作。
readLineData(maxlen:int) PyObject 将最多maxSize个字符读取到数据中,并返回读取的字符数。

此函数由readLine()调用,并使用getChar()提供其基本实现。缓冲设备可以通过重新实现此函数来提高readLine()的性能。

readLine()将一个”\0″字节附加到数据中;readLineData()不需要执行此操作。

如果重新实现此函数,请小心返回正确的值:它应该返回此行中读取的字节数,包括终止换行符,如果此时没有要读取的行,则返回0。如果发生错误,当且仅当没有读取字节时,它应该返回-1。读取超过EOF被认为是一个错误。
canReadLine() bool 如果可以从设备中读取完整的数据行,则返回true;否则返回false。

请注意,没有缓冲区的设备无法确定可以读取的内容,总是返回false。

此函数通常与readyRead()信号一起调用。

重新实现此函数的子类必须调用基本实现,以便包含QIODevices缓冲区的内容。例子:

def canReadLine(self):

return buffer.contains(‘\n’)or QIODevice.canReadLine()

putChar(c:str) bool 将字符c写入设备。成功时返回true;否则返回false。
getChar(c: bytes) bool 从设备中读取一个字符并将其存储在c中。如果c为None,则丢弃该字符。成功时返回true;否则返回false。
ungetChar(c: str) None 将字符c放回设备中,并递减当前位置,除非位置为0。这个函数通常被调用来”撤消”getChar()操作,例如在编写回溯解析器时。

如果之前没有从设备中读取c,则该行为是未定义的。
peek(maxlen:int) PySide6.QtCore.QByteArray 这是一个重载函数。

从设备中窥视最多maxSize字节,返回作为QByteArray窥视的数据。

例子:

isExeFile = bool(QFile file)

return file.peek(2)==“MZ”

此功能无法报告错误;返回一个空的QByteArray可能意味着当前没有可用于窥视的数据,或者发生了错误。

write(data:Union[QByteArray,bytes]) int 这是一个重载函数。

将数据的内容写入设备。返回实际写入的字节数,如果发生错误,则返回-1。
writeData(data: str,len: int) int 将数据中最多maxSize个字节写入设备。返回写入的字节数,如果发生错误,则返回-1。

此函数由QIODevice调用。在创建QIODevicece的子类时重新实现此函数。

当重新实现此函数时,重要的是此函数在返回之前写入所有可用的数据。这是QDataStream能够对类进行操作所必需的。QDataStream假定所有信息都已写入,因此在出现问题时不会重试写入。
setCurrentReadChannel(int) None 将QIODevice的当前读取通道设置为给定通道。当前输入通道由函数read()、readAll()、readLine()和getChar()使用。它还确定哪个通道触发QIODevices发出readyRead()。
setCurrentWriteChannel(int) None 将QIODevice的当前写入通道设置为给定通道。当前输出通道由函数write()、putChar()使用。它还确定哪个通道触发QIODevices来发出bytesWritten()。
currentReadChannel() int 返回当前读取通道的索引。
currentWriteChannel() int 返回当前写入通道的索引。
readChannelCount() int 如果设备处于打开状态,则返回可用的读取通道数;否则返回0。
writeChannelCount() int 如果设备处于打开状态,则返回可用写入通道的数量;否则返回0。
bytesToWrite() int 对于缓冲设备,此函数返回等待写入的字节数。对于没有缓冲区的设备,此函数返回0。

重新实现此函数的子类必须调用基本实现,以便包括QIODevices的缓冲区大小。
bytesAvailable() None 返回可供读取的字节数。此函数通常与顺序设备一起使用,以确定在读取之前要在缓冲区中分配的字节数。

重新实现此函数的子类必须调用基本实现,以便包括QIODevices的缓冲区大小。例子:

def bytesAvailable(self):

return buffer.size()+ QIODevice.bytesAvailable()

setErrorString(str) None 设置str上一次设备错误的可读描述。
errorString() Str 返回上一次发生的设备错误的可读说明。
isReadable() bool 如果可以从设备中读取数据,则返回true;否则返回false。使用bytesAvailable()确定可以读取的字节数。

这是一个方便功能,用于检查设备的OpenMode是否包含ReadOnly标志。
isSequential() bool 如果此设备是连续的,则返回true;否则返回false。

与随机访问设备相反,顺序设备没有开始、结束、大小或当前位置的概念,并且它们不支持搜索。只有当设备报告数据可用时,您才能从设备中读取。顺序设备最常见的例子是网络套接字。在Unix上,诸如/dev/zero和fifo管道之类的特殊文件是按顺序排列的。

另一方面,常规文件确实支持随机访问。它们既有大小,也有当前位置,还支持在数据流中前后搜索。常规文件是非连续的。
isTextModeEnabled() bool 如果启用了Text标志,则返回true;否则返回false。
isWritable() bool 如果数据可以写入设备,则返回true;否则返回false。

这是一个方便功能,用于检查设备的OpenMode是否包含WriteOnly标志。
atEnd() bool 如果当前读写位置在设备的末尾(即设备上没有更多可供读取的数据),则返回true;否则返回false。

对于某些设备,即使有更多的数据要读取,atEnd()也可以返回true。这种特殊情况仅适用于直接响应您调用read()生成数据的设备(例如,Unix和macOS上的/dev/或/proc文件,或所有平台上的控制台输入/stdin)。
seek(pos: int) bool 对于随机访问设备,此函数将当前位置设置为pos,成功时返回true,发生错误时返回false。对于顺序设备,默认行为是生成警告并返回false。

当对QIODevicece进行子类化时,必须在函数开始时调用QIODevice::seek(),以确保QIODevicee内置缓冲区的完整性。
pos() int 对于随机访问设备,此函数返回数据写入或读取的位置。对于顺序设备或闭合设备,如果没有”当前位置”的概念,则返回0。

设备的当前读/写位置由QIODevices内部维护,因此无需重新实现此功能。当对QIODevicece进行子类化时,请使用seek()通知QIODevices设备位置的变化。
reset() bool 寻找随机接入设备的输入开始。成功时返回true;否则返回false(例如,如果设备未打开)。

请注意,当在QFile上使用QTextStream时,对QFile调用reset()将不会得到预期的结果,因为QTextStream会缓冲文件。请改用seek()函数。
startTransaction() None 在设备上启动新的读取事务。

定义读取操作序列中的可恢复点。对于顺序设备,读取数据将在内部复制,以便在读取不完整的情况下进行恢复。对于随机访问设备,此功能保存当前位置。调用commitTransaction()或rollbackTransaction(。
rollbackTransaction() None 回滚已读事务。

将输入流恢复到startTransaction()调用的点。当在提交事务之前检测到不完整的读取时,此函数通常用于回滚事务。
commitTransaction() None 完成读取事务。

对于顺序设备,事务期间记录在内部缓冲区中的所有数据都将被丢弃。
isTransactionStarted() bool 如果设备上正在进行事务,则返回true,否则返回false。
size() int 对于开放式随机访问设备,此函数返回设备的大小。对于打开的顺序设备,返回bytesAvailable()。

如果设备已关闭,返回的大小将不会反映设备的实际大小。
skip(int) int 跳过指定数量的字节,返回实际跳过的 字节数

从设备中跳过最多maxSize字节。返回实际跳过的字节数,错误时返回-1。

此函数不等待,只丢弃已可供读取的数据。

如果设备以文本模式打开,则行尾终止符将转换为”\n”符号,并作为单个字节计数,与read()和peek()行为相同。

此函数适用于所有设备,包括无法查找()的顺序设备。它经过优化,可以在peek()调用后跳过不需要的数据。

对于随机访问设备,可以使用skip()从当前位置向前搜索。不允许使用负的maxSize值。
skipData(maxSize:int) int 从设备中跳过最多maxSize字节。返回实际跳过的字节数,错误时返回-1。

此函数由QIODevice调用。在创建QIODevicece的子类时,请考虑重新实现它。

基本实现通过读取到伪缓冲区来丢弃数据。这很慢,但适用于所有类型的设备。子类可以重新实现此函数以对此进行改进。
waitForBytesWritten(msecs:int) bool 对于缓冲设备,此函数将等待,直到缓冲写入数据的有效负载已写入设备并发出bytesWritten()信号,或者直到毫秒过去。如果毫秒为-1,则此功能不会超时。对于未缓冲的设备,它会立即返回。

如果数据的有效负载已写入设备,则返回true;否则返回false(即,如果操作超时或发生错误)。

此函数可以在没有事件循环的情况下运行。它在编写非GUI应用程序和在非GUI线程中执行I/O操作时非常有用。

如果从连接到bytesWritten()信号的插槽中调用,则bytesWriten()将不会重新出现。

重新实现此函数以为自定义设备提供阻塞API。默认实现不执行任何操作,并返回false。
waitForReadyRead(msecs:int) bo01 块,直到新数据可用于读取并且readyRead()信号已发出,或者直到毫秒过去。如果毫秒为-1,则此功能不会超时。

如果有新数据可供读取,则返回true;否则返回false(如果操作超时或发生错误)。

此函数可以在没有事件循环的情况下运行。它在编写非GUI应用程序和在非GUI线程中执行I/O操作时非常有用。

如果从连接到readyRead()信号的插槽中调用,则不会重新发出readyRead()。

重新实现此函数以为自定义设备提供阻塞API。默认实现不执行任何操作,并返回false。



QIODevice信号

信号 描述
aboutToClose() 该信号是在设备即将关闭时发出的。如果您有需要在设备关闭前执行的操作(例如,如果您在单独的缓冲区中有数据需要写入设备),请连接此信号。
bytesWritten(bytes:int) 每当有效载荷的数据被写入设备的当前写入通道时,就会发出该信号。字节参数设置为此有效负载中写入的字节数。

bytesWritten()不是递归发出的;如果重新进入事件循环或在连接到bytesWritten()信号的插槽内调用waitForBytesWritten。
channelBytesWritten(channel:int,bytes:int) 每当数据的有效载荷被写入设备时,就会发出该信号。bytes参数设置为写入此有效负载的字节数,而channel是写入的通道。与bytesWritten()不同,它是在不考虑当前写入通道的情况下发出的。

channelBytesWritten()可以递归地发出,即使对于同一个通道也是如此。
channelReadyRead(channel:int) 当新的数据可用于从设备中读取时,会发出该信号。通道参数设置为数据到达的读取通道的索引。与readyRead()不同,它是在不考虑当前读取通道的情况下发出的。

channelReadyRead()可以递归地发出,即使对于同一个通道也是如此。
readChannelFinished() 当输入(读取)流在此设备中关闭时,会发出此信号。它在检测到关闭时立即发出,这意味着可能仍有可用的数据可用于读取read()。
readyRead() 每当有新数据可用于从设备的当前读取通道读取时,该信号就会发出一次。只有当新数据可用时,例如当网络数据的新负载到达网络套接字时,或者当新的数据块被附加到设备时,它才会再次发出。

readyRead()不是递归发出的;如果您重新进入事件循环或在连接到readyRead()信号的插槽内调用waitForReadyRead(),则该信号将不会再次出现(尽管waitForReadRead()仍可能返回true)。

对于实现从QIODevicece派生的类的开发人员来说,请注意:当新数据到达时,您应该始终发出readyRead()(不要只因为缓冲区中还有数据要读取而发出)。不要在其他条件下发出readyRead()。



版权声明:本文为qq_40597070原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。