简体   繁体   English

为什么print()影响com1的读取方式?

[英]why does a print() affect how com1 is read?

I'm writing an interface for an old piece of electronic equipment that uses RS232 serial. 我正在为使用RS232串行接口的旧电子设备编写接口。 I've run into a problem that I can't seem to solve. 我遇到了一个似乎无法解决的问题。 Here is the original code 这是原始代码

def readMyPort():
    global readPort
    while True:   #always loop
        if readPort: # only do something of the port is active
            dataString = b''
            while (mySerialPort.inWaiting()>0):
                data = mySerialPort.read(1)
                if (data == b'') or (data == b'\r') or (data == b'\n'):
                    if (dataString != b''):
                        myOutput.insert('1.0', (dataString + b'\n').decode())
                        dataString = b''
                else:
                    dataString += data

The problem I face is that the instrument sends a string of 12 characters in response to a command, and I only seem to catch the last 4, and no, there are no '', '\\r', or '\\n' in the string. 我面临的问题是乐器响应命令发送了一个12个字符的字符串,而且我似乎只捕获了最后4个字符,不,里面没有”,“ \\ r”或“ \\ n”字符串。 In an effort to troubleshoot I added a print(), as shown below. 为了进行故障排除,我添加了print(),如下所示。 Magically I started to get all the data. 神奇的是,我开始获取所有数据。

def readMyPort():
    global readPort
    while True:   #always loop
        if readPort: # only do something of the port is active
            dataString = b''
            while (mySerialPort.inWaiting()>0):
                data = mySerialPort.read(1)
                print(data)   #<-------- the added line
                if (data == b'') or (data == b'\r') or (data == b'\n'):
                    if (dataString != b''):
                        myOutput.insert('1.0', (dataString + b'\n').decode())
                        dataString = b''
                else:
                    dataString += data

Now I don't want to have all that printing going on normally. 现在,我不想让所有打印正常进行。 I tried just adding a print('') and that works as well, but I still have all those \\n getting printed. 我尝试只添加一个print('') ,它也能正常工作,但是我仍然打印了所有\\ n。 I tried print('', end = '\\r') but that didn't work. 我尝试了print('', end = '\\r')但是没有用。 Does anyone have an idea why? 有谁知道为什么? I don't think it is a speed issue. 我认为这不是速度问题。 I'm only running 9600 baud. 我只运行9600波特。 FYI: python 3.2 on a Win32 machine. 仅供参考:Win32机器上的python 3.2。 This routine is launched in it's own thread. 该例程在其自己的线程中启动。

The operation print(data) requires some time (relatively large) to print something to the console. print(data)操作需要一些时间(相对较长)才能将某些内容打印到控制台。 So by adding the line print(data) you just add some delay inside your loop. 因此,通过添加行print(data)您只需在循环内部添加一些延迟。 You may verify this theory by substituting print(data) for time.sleep(0.1 or whatever small value) and checking that the problem is hopefully gone. 您可以通过将print(data)替换为time.sleep(0.1 or whatever small value)并检查问题是否有望解决,从而验证该理论。

I think that the delay helps because without it mySerialPort.inWaiting() may becomes 0 sometimes (receive buffer is empty) before the transaction is actually completed. 我认为延迟会mySerialPort.inWaiting()帮助,因为如果没有延迟, mySerialPort.inWaiting()有时可能在事务实际完成之前变为0 (接收缓冲区为空)。 Your instrument can't simply output data that fast. 您的仪器不能简单地以如此快的速度输出数据。 In your final version of the code you may add time.sleep() instead of print(data) . 在代码的最终版本中,您可以添加time.sleep()而不是print(data)

Following the answer of Konstantin, it appears that the serial port needs some time to adjust the buffer and counters, so adding a small delay in the loop solved my problem. 按照康斯坦丁的答案,看来串行端口需要一些时间来调整缓冲区和计数器,因此在循环中添加一个小的延迟就解决了我的问题。 1 ms is not enough but 10 ms is. 1 ms是不够的,但是10 ms是足够的。 The final code is: 最终的代码是:

def readMyPort():
    global readPort
    while True:   #always loop
        if readPort: # only do something if the port is active
            dataString = b''
            while (mySerialPort.inWaiting()>0):  #if something is in the buffer
                data = mySerialPort.read(1)
                if (data == b'') or (data == b'\r') or (data == b'\n'):
                    if (dataString != b''):  #don't output empty strings
                        myOutput.insert('1.0', (dataString + b'\n').decode())
                        dataString = b''
                else:
                    dataString += data
                    time.sleep(0.01)   #slow the loop down a bit 

I do continue to wonder if there is a more elegant solution. 我仍然想知道是否有更优雅的解决方案。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM