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

Python struct构造bytearray串口循环发送校验和错误修复

校验和错误原因

你的while循环段代码存在3处问题,直接导致校验和计算失败:

  • 校验和遍历循环的计数变量是y,但读取数组元素时错误使用了外层第一次计算校验和遗留的变量x(第一次for循环结束后x值固定为74),循环全程没有遍历4~74位的所有字节,一直在重复累加array1[74]这一个位置的值
  • 每次进入循环计算新的校验和前,没有将check_sum变量重置为0,会在上一次计算的结果基础上继续累加,数值持续累积后取模的结果完全不符合校验规则
  • 计数器counter持续自增未做截断,当值超过255时,赋值给单字节长度的array1[5]会触发值溢出错误
修复方案

将while循环段的逻辑修正即可,修复后可正常连续传输数据,核心修改点:

  1. 每次计算校验和前将check_sum重置为0
  2. 遍历校验段时使用当前循环变量y读取对应字节值
  3. 计数器赋值时做模256处理,适配单字节存储要求

修复后的完整可运行代码:

import serial
import struct
import time

ser = serial.Serial('COM16', 19200, serial.EIGHTBITS, serial.PARITY_NONE, serial.STOPBITS_ONE)
size = 78
array1 = bytearray(size)

array1[0] = 0xFF
array1[1] = 0xFF
array1[2] = 0x54
array1[3] = 0x52
array1[5] = 0
array1[76] = 0x0D
array1[77] = 0x0A

counter = 0

altitude = input("altitude: ")
altitude_gps = input("gps altitude: ")
locationx = input("location x: ")
locationy = input("location y : ")
payload_altitude = input("payload altitude: ")
locationx_payload = input("location x payload:  ")
locationy_paylaod = input("location y payload: ")

altitude_array = struct.pack('<f', float(altitude))
altitude_gps_array = struct.pack('<f', float(altitude_gps))
locationx_array = struct.pack('<f', float(locationx))
locationy_array = struct.pack('<f', float(locationy))
payload_altitude_array = struct.pack('<f', float(payload_altitude))
locationx_payload_array = struct.pack('<f', float(locationx_payload))
locationy_paylaod_array = struct.pack('<f', float(locationy_paylaod))

array1[6] = altitude_array[0]
array1[7] = altitude_array[1]
array1[8] = altitude_array[2]
array1[9] = altitude_array[3]

array1[10] = altitude_gps_array[0]
array1[11] = altitude_gps_array[1]
array1[12] = altitude_gps_array[2]
array1[13] = altitude_gps_array[3]

array1[14] = locationx_array[0]
array1[15] = locationx_array[1]
array1[16] = locationx_array[2]
array1[17] = locationx_array[3]

array1[18] = locationy_array[0]
array1[19] = locationy_array[1]
array1[20] = locationy_array[2]
array1[21] = locationy_array[3]

array1[22] = payload_altitude_array[0]
array1[23] = payload_altitude_array[1]
array1[24] = payload_altitude_array[2]
array1[25] = payload_altitude_array[3]

array1[26] = locationx_payload_array[0]
array1[27] = locationx_payload_array[1]
array1[28] = locationx_payload_array[2]
array1[29] = locationx_payload_array[3]

array1[30] = locationy_paylaod_array[0]
array1[31] = locationy_paylaod_array[1]
array1[32] = locationy_paylaod_array[2]
array1[33] = locationy_paylaod_array[3]

# 首次发送
check_sum = 0
for x in range(4, 75):
    check_sum += array1[x]
check_sum = check_sum % 256
array1[75] = check_sum
ser.write(array1)
time.sleep(3)

while True:
    counter = counter + 1
    array1[5] = counter % 256  # 单字节截断,避免值溢出
    # 每次计算校验和前重置为0
    check_sum = 0
    # 用正确的循环变量y遍历
    for y in range(4, 75):
        check_sum += array1[y]
    check_sum = check_sum % 256
    array1[75] = check_sum
    ser.write(array1)
    time.sleep(3)

注:如果你的协议要求计数器是多字节长度,可根据实际协议调整counter的字节拆分逻辑,不要直接赋值给单字节位置即可。

内容的提问来源于stack exchange,提问作者Inertial Measurement Unit

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.28 04:48:16