You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用OpenCV+PySerial向Arduino发送条码数据遇TypeError错误求助

问题分析与解决:串口发送条码数据报错TypeError

我使用OpenCV读取条码,通过pyserial库与Arduino进行串口通信,目标是实现类似亚马逊仓库的机械臂移动物体功能,但发送数据时出现如下错误:

C:\Users\arcco\venv\Scripts\python.exe D:\Python\pythonProject\test.py 
Traceback (most recent call last):
  File "D:\Python\pythonProject\test.py", line 45, in <module>
    img = decode(img)
          ^^^^^^^^^^^
  File "D:\Python\pythonProject\test.py", line 19, in decode
    ser.write (a)
  File "C:\Users\arcco\venv\Lib\site-packages\serial\serialwin32.py", line 310, in write
    data = to_bytes(data)
           ^^^^^^^^^^^^^^
  File "C:\Users\arcco\venv\Lib\site-packages\serial\serialutil.py", line 68, in to_bytes
    return bytes(bytearray(seq))
                 ^^^^^^^^^^^^^^
TypeError: 'bytes' object cannot be interpreted as an integer
detected barcode: Decoded(data=b'43770929851162', type='I25', rect=Rect(left=62, top=0, width=694, height=180), polygon=[Point(x=62, y=1), Point(x=62, y=179), Point(x=756, y=180), Point(x=756, y=0)], quality=181, orientation='UP')
Type: I25
Data: b'43770929851162'


Process finished with exit code 1

代码片段

尝试向串口发送字节数组的代码如下:

from pyzbar import pyzbar
import cv2
import serial

ser = serial.Serial("COM3", 9600)

def decode(image):
    # decodes all barcodes from an image
    decoded_objects = pyzbar.decode(image)
    for obj in decoded_objects:
        # draw the barcode
        print("detected barcode:", obj)
        image = draw_barcode(obj, image)
        # print barcode type & data
        print("Type:", obj.type)
        print("Data:", obj.data)
        print()
        a = (bytes([obj.data]))
        ser.write(bytes(a))

    return image


def draw_barcode(decoded, image):
    # n_points = len(decoded.polygon)
    # for i in range(n_points):
    #     image = cv2.line(image, decoded.polygon[i], decoded.polygon[(i+1) % n_points], color=(0, 255, 0), thickness=5)
    # uncomment above and comment below if you want to draw a polygon and not a rectangle
    image = cv2.rectangle(image, (decoded.rect.left, decoded.rect.top),
                            (decoded.rect.left + decoded.rect.width, decoded.rect.top + decoded.rect.height),
                            color=(0, 255, 0),
                            thickness=5)
    return image


if __name__ == "__main__":
    from glob import glob

    barcodes = glob("barcode*.png")
    for barcode_file in barcodes:
        # load the image to opencv
        img = cv2.imread(barcode_file)
        # decode detected barcodes & get the image
        # that is drawn
        img = decode(img)
        # show the image
        cv2.imshow("img", img)
        cv2.waitKey(0)

错误原因

核心问题出在这两行代码:

a = (bytes([obj.data]))
ser.write(bytes(a))

从打印的Data: b'43770929851162'可以看到,obj.data本身已经是bytes类型,但你把它放到列表[obj.data]中传给bytes(),bytes()会尝试把列表中的每个元素当成整数来生成字节数组,而bytes对象无法被解析为整数,因此触发了TypeError。此外,后续又多套了一层bytes(a),属于冗余操作。

解决方法

根据需求选择以下两种方式之一修改代码:

  1. 直接发送原始条码数据
    既然obj.data已经是符合串口要求的bytes类型,直接传给ser.write()即可:

    # 替换原来的a = ...和ser.write(...)
    ser.write(obj.data)
    
  2. 添加结束符发送(推荐,适配Arduino接收逻辑)
    通常Arduino需要通过换行符或特定字符判断数据接收完成,因此可以将条码数据转成字符串后添加换行符,再编码为bytes发送:

    # 替换原来的a = ...和ser.write(...)
    # 解码bytes为字符串,添加换行符后重新编码
    barcode_str = obj.data.decode('utf-8') + '\n'
    ser.write(barcode_str.encode('utf-8'))
    

额外注意事项

  • 确保Arduino端的串口波特率与Python代码中的9600一致
  • 可以添加串口连接异常处理,避免因串口未打开导致的报错
  • 测试时可以先在Arduino端编写简单的串口打印代码,验证数据是否正确接收

内容的提问来源于stack exchange,提问作者Arcco Playz

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.08 22:45:38