Python serial(pySerial)使用EOL \ r而不是\ n读取行

时间:2017-07-20 13:13:26

标签: python python-3.x pyserial carriage-return eol

我正在通过RS232电缆与SR830锁相放大器通信。在读取数据时,如下面的代码:

import serial

def main():
    ser = serial.Serial(
        port='COM6',
        baudrate=19200,
        parity=serial.PARITY_NONE,
        stopbits=serial.STOPBITS_ONE,
        bytesize=serial.EIGHTBITS)
    ser.timeout=1
    ser.write("OUTP? 1 \r\n".encode()) #Asks the Lock-in for x-value
    ser.write("++read\r\n".encode())
    x=ser.readline()
    print (x)
if __name__ == '__main__': main()

我得到一个像b'-3.7486e-008\r'这样的字节字符串。但是ser.readline()函数无法将\ r \ n识别为EOL。因此,每次读取数据时都要等待超时,这很麻烦,因为我想尽可能快地占用很多分数。并且数字的长度变化很大,因此我不能仅使用ser.read(12)。我尝试过使用io.TextIOWrapper,但我不清楚如何实现它。这是我的尝试:

import serial
import io
def main():
    ser = serial.Serial(
        port='COM6',
        baudrate=19200,
        parity=serial.PARITY_NONE,
        stopbits=serial.STOPBITS_ONE,
        bytesize=serial.EIGHTBITS)
    ser.timeout=1
    sio = io.TextIOWrapper(io.BufferedRWPair(ser, ser))
    sio.write("OUTP? 1 \r\n") #Asks the Lock-in for x-value
    sio.write("++read\r\n")
    x=sio.readline()
    print (x)
if __name__ == '__main__': main()

只打印一个空格。任何帮助将不胜感激,谢谢。

编辑: 这是我在答案后的工作代码,使用循环:

import serial
def main():
    ser = serial.Serial(
        port='COM6',
        baudrate=19200,
        parity=serial.PARITY_NONE,
        stopbits=serial.STOPBITS_ONE,
        bytesize=serial.EIGHTBITS)
    ser.timeout=5
    ser.write("OUTP? 1 \r\n".encode()) #Asks the Lock-in for x-value
    ser.write("++read\r\n".encode())
    buffer = ""
    while True:
        oneByte = ser.read(1)
        if oneByte == b"\r":    #method should returns bytes
            print (buffer)
            break
        else:
            buffer += oneByte.decode()
if __name__ == '__main__': main()

3 个答案:

答案 0 :(得分:4)

如何使用简单的循环进行阅读?

def readData():
    buffer = ""
    while True:
        oneByte = ser.read(1)
        if oneByte == b"\r":    #method should returns bytes
            return buffer
        else:
            buffer += oneByte.decode("ascii")

您可以检查Pyserial包中的serialutil.py文件,它们使用相同的方法来实现方法read_until

答案 1 :(得分:1)

来自the docs for readline()

  

对于二进制文件,行终止符始终为b'\n';对于文本文件,newline的{​​{1}}参数可用于选择已识别的行终止符。

当然,你不能在这里使用open()。但是你可以做的是使用open将字节流转换为文本流:

io.TextIOWrapper

答案 2 :(得分:0)

改为使用read_until():

ser.read_until(b'\ r')

请注意,不要忘记b。否则,即使它读取了“ \ r”,该函数也不会返回,直到达到端口上设置的超时时间为止。