使用Python处理ADC激光测距数据并绘制为图片(二)

使用Python处理ADC激光测距数据并绘制为图片

  • 说明
  • 一、定义全局变量变
  • 二、保存和清空原始数据
  • 三、拆分原始数据为键值对
  • 四、获取标题、FigText、更新统计信息文件
  • 五、生成图片
  • 六、处理原始数据文件
  • 七、主函数入口
  • 八、测试结果

说明

1. 主要是将ADC激光测距叠加后的1024Byte数据绘制为图片,便于直观的分析与观察

一、定义全局变量变


import os
import shutilimport matplotlib.pyplot as plt# 原始数据
OrgDataDir = 'DataHandlerDir' #原始数据目录
OrgDataName = 'COM3-115200-2023-08-03-14-22-49-650m' #原始文件名称
OrgDataExtension = '.log' #原始文件拓展名
OrgDataFullDirNameExt = OrgDataDir + '/' + OrgDataName + OrgDataExtension #全路径
OrgDataFilesGroup = list()# 处理后数据
CreatDataFatherDir = 'ImageCreatDir' #目录
CreatDataDir = OrgDataName
CreatDataName = OrgDataName
CreatDataExtension = '.txt' #统计文件扩展名
CreatDataNameExtension = CreatDataName + CreatDataExtension
CreatDataImageFullDir = CreatDataFatherDir + '/' + CreatDataDir
CreatDataStaFullDirNameExt = CreatDataFatherDir + '/' + CreatDataDir + '/' + CreatDataName + CreatDataExtension# FigText序号范围
FigTextStartIndex = 1024
FigTextEndIndex = 1030# 峰值及索引
OrgDataPeakValue = 0  # 峰值
OrgDataPeakIndex = 0  # 峰值索引
OrgDataPeakValue50 = 0  # 峰值50%
OrgDataPeakValue60 = 0  # 峰值60%
OrgDataPeakIndexGap = 50  # 峰值索引间隔
OrgDataPeakIndexLeft = 0  # 峰值索引左值
OrgDataPeakIndexRigth = 0  # 峰值索引右值AtcDataHeaderStr = '[0000]'  # 有效数据头
OrgDataValSize = 1024  # ADC数据项大小
OrgDataMemory = {}  # 原始数据缓存
UpdateImageCount = 0  # 图片计数
AxisX = list()  # 横坐标
AxisY = list()  # 纵坐标

二、保存和清空原始数据


# 保存原始数据
def Store_OrgData_KeyVal(key, val):global OrgDataMemoryOrgDataMemory[key] = val# 清空原始数据缓存
def Clear_OrgData_Memory():global OrgDataMemoryglobal AxisXglobal AxisYglobal OrgDataPeakValueglobal OrgDataPeakIndexglobal OrgDataPeakValue60global OrgDataPeakValue50global OrgDataPeakIndexLeftglobal OrgDataPeakIndexRigthglobal UpdateImageCountOrgDataMemory.clear()AxisX.clear()AxisY.clear()OrgDataPeakValue = 0OrgDataPeakIndex = 0OrgDataPeakValue60 = 0OrgDataPeakValue50 = 0OrgDataPeakIndexLeft = 0OrgDataPeakIndexRigth = 0

三、拆分原始数据为键值对


# 拆分键值对
def Split_OrgData_KeyVal():global OrgDataMemoryglobal OrgDataPeakValueglobal OrgDataPeakIndexglobal OrgDataPeakValue50global OrgDataPeakValue60global OrgDataPeakIndexGapglobal OrgDataPeakIndexLeftglobal OrgDataPeakIndexRigthglobal AxisXglobal AxisYi = 0peakVal = 0for xKey, yVal in OrgDataMemory.items():AxisX.append(int(xKey))AxisY.append(int(yVal))# 寻找峰值及索引peakVal = int(yVal)if peakVal > OrgDataPeakValue:OrgDataPeakValue = peakValOrgDataPeakIndex = int(xKey)i += 1if i >= OrgDataValSize:OrgDataPeakValue60 = OrgDataPeakValue * 0.6  # 峰值50%OrgDataPeakValue50 = OrgDataPeakValue * 0.5  # 峰值60%# 峰值左间隔OrgDataPeakIndexLeft = OrgDataPeakIndex - OrgDataPeakIndexGapif OrgDataPeakIndexLeft < 0:OrgDataPeakIndexLeft = 0# 峰值右间隔OrgDataPeakIndexRigth = OrgDataPeakIndex + OrgDataPeakIndexGapif OrgDataPeakIndexRigth > OrgDataValSize - 1:OrgDataPeakIndexRigth = OrgDataValSize - 1return

四、获取标题、FigText、更新统计信息文件


# 获取FigText
def GetFigText():global OrgDataMemoryglobal FigTextStartIndexglobal FigTextEndIndexresStr = ''for i in range(FigTextStartIndex, FigTextEndIndex + 1):txt = OrgDataMemory[str(i)]resStr += txt + '\n'# print("GetFigText:", resStr)return resStr# 获取标题
def GetTitleText():global OrgDataPeakIndexglobal OrgDataPeakIndexLeftglobal OrgDataPeakIndexRigthglobal OrgDataPeakValueresStr = "xCenter:%s  xLeft:%s  xRight:%s  Peak:%s" % ( \str(OrgDataPeakIndex), \str(OrgDataPeakIndexLeft), \str(OrgDataPeakIndexRigth), \str(OrgDataPeakValue))# print("TitleText:", resStr)return resStr# 获取图片名称
def Get_Image_Name():global OrgDataMemoryglobal FigTextEndIndextxtStr = str(OrgDataMemory[str(FigTextEndIndex)])index = txtStr.find('Gears:')if index != -1:name = txtStr[index:].strip().replace(':', '').replace(' ', '-')else:name = 'Gears0-Superpos0-Dist0dm'picName = str(OrgDataMemory[str(FigTextEndIndex + 1)]) + '-' + namereturn picName# 更新统计信息
def Update_StaInfo(staFileFullName, txt):global OrgDataPeakValuewith open(staFileFullName, 'a+', encoding='utf-8') as file:# strTxt = '[{}]  '.format(int(UpdateImageCount)) + txtstrTxt = '[%04u] ' % UpdateImageCount + txtresTxt = strTxt + " ==> Peak:" + str(OrgDataPeakValue) + "\n"file.write(resTxt)print(resTxt, end='')

五、生成图片

# 生成图片
def OrgData_CreateImage(staFileDir, staFileFullName):global AxisXglobal AxisYglobal OrgDataPeakIndexglobal OrgDataPeakIndexLeftglobal OrgDataPeakIndexRigthglobal OrgDataPeakValueglobal OrgDataPeakValue50global OrgDataPeakValue60global CreatDataImageFullDirglobal UpdateImageCountSplit_OrgData_KeyVal()plt.figure(figsize=(12, 8))plt.title(GetTitleText())plt.xlabel("Sampling Point")plt.ylabel("Superposition Data")plt.plot(AxisX, AxisY, 'ro', linewidth=2)plt.axvline(OrgDataPeakIndex)plt.axvline(OrgDataPeakIndexLeft, color="green", linestyle="--")plt.axvline(OrgDataPeakIndexRigth, color="green", linestyle="--")plt.axhline(OrgDataPeakValue, color="red")plt.axhline(int(OrgDataPeakValue50), color="blue")plt.axhline(int(OrgDataPeakValue60), color="blue")plt.text(600, int(OrgDataPeakValue), 'Peak={}'.format(int(OrgDataPeakValue)), fontsize=16, fontweight='bold', color="black", ha='left', va='center')plt.text(300, int(OrgDataPeakValue50), '50%Peak={}'.format(int(OrgDataPeakValue50)), fontsize=16, fontweight='bold', color="black", ha='left', va='center')plt.text(600, int(OrgDataPeakValue60), '60%Peak={}'.format(int(OrgDataPeakValue60)), fontsize=16, fontweight='bold', color="black", ha='left', va='center')plt.figtext(0.15, 0.7, GetFigText(), color='blue', fontsize=12, ha="left", va="center")UpdateImageCount += 1picName = Get_Image_Name()serial = '[%04u]' % UpdateImageCountpicDirName = staFileDir + '/' + serial + picName + ".png"plt.savefig(picDirName, dpi=300, bbox_inches="tight")Update_StaInfo(staFileFullName, picName)plt.close()Clear_OrgData_Memory()

六、处理原始数据文件

# 处理原始数据文件
def File_OrgData_Handler(orgDatFullName, staFileDir, staFileFullName):global AtcDataHeaderStrglobal FigTextEndIndexwith open(orgDatFullName, 'r', encoding='utf-8') as fileHander:  # 打开文件actDataHeaderFlg = 0  # 有效数据头indexCount = 0  # 索引计数for lineTxet in fileHander:  # 读取一行数据if actDataHeaderFlg == 0:  # 数据头无效if AtcDataHeaderStr in lineTxet:  # 包含数据头startIndex = lineTxet.find(AtcDataHeaderStr)  # 数据头位置if startIndex != -1:  # 位置有效endIndex = lineTxet.find(']', startIndex)if endIndex != -1:key = lineTxet[startIndex + 1: endIndex].strip()  # 截取数据val = lineTxet[endIndex + 1:].strip()if key.isdigit() == True and val.isdigit() == True:  # 都为数字Clear_OrgData_Memory()  # 清空缓存Store_OrgData_KeyVal(key, val)  # 保存数据actDataHeaderFlg = 1  # 数据头有效indexCount = 0else:indexCount = indexCount + 1  # 计数加1indexHeader = '[%04u]' % indexCountif indexCount <= (OrgDataValSize - 1):  # ADC数据0~1023if indexHeader in lineTxet:  # 包含ADC数据索引start = lineTxet.find(indexHeader)  # 索引有效end = lineTxet.find(']', start)if start != -1 and end != -1:key = lineTxet[start + 1: end].strip()  # 截取数据去掉前后空格val = lineTxet[end + 2:].strip()if key.isdigit() == True and val.isdigit() == True:  # 都为数字Store_OrgData_KeyVal(key, val)  # 保存数据continueClear_OrgData_Memory()actDataHeaderFlg = 0indexCount = 0else:  # 其他数据1024以后start = lineTxet.find(']')if start != -1:  # 索引有效val = lineTxet[start + 1:].strip()if len(val) != 0 and val != '':  # 有内容Store_OrgData_KeyVal(str(indexCount), val)  # 保存数据if val.find('ADC Meas Complete ==> Gears:') != -1:  # 结束标准timesTick = lineTxet[1: start].strip().replace(' ', '-').replace(':', '-')  # 截取数据Store_OrgData_KeyVal(str(indexCount + 1), timesTick)  # 保存数据FigTextEndIndex = indexCountactDataHeaderFlg = 0indexCount = 0# name = os.path.splitext(os.path.basename(dirName))[0]# dir  = os.path.join(CreatDataFatherDir, name)if os.path.exists(staFileDir):OrgData_CreateImage(staFileDir, staFileFullName)else:indexCount = indexCount - 1else:Clear_OrgData_Memory()actDataHeaderFlg = 0indexCount = 0

七、主函数入口

# 删除目录内容
def Delete_Directory_Content(dir):if os.path.exists(dir) == True:  # 目录存在for item in os.listdir(dir):  # 目录中内容name = os.path.join(dir, item)  # 拼接完整路径if os.path.isfile(name):os.remove(name)  # 删除目录elif os.path.isdir(name):shutil.rmtree(name)  # 删除文件# 判断基本目录
def Judg_BasicDir_Info(datDir, creatDir):res = 0if not os.path.exists(datDir):  # 目录不存在print(datDir, "Directory No Exists, ", end='')os.mkdir(datDir)  # 创建目录print("Create Successful......")res = 1if not os.path.exists(creatDir):  # 目录不存在print(creatDir, "Directory No Exists, ", end='')os.mkdir(creatDir)  # 创建目录print("Create Successful......")res = 2return res# 创建图片目录和统计文件
def Create_DataImage_DirFile(dir, name):if not os.path.exists(dir):  # 图片目录不存在os.mkdir(dir)else:Delete_Directory_Content(dir)dirName = os.path.join(dir, name)open(dirName, 'a').close()  # 创建统计文件print('dirName:', dirName)# 获取所有原始数据文件
def Get_OrgData_FilesGroup(dir, extName):res = 1fileGroup = list()fileList = os.listdir(dir)  # 获取目录中内容for file in fileList:if file.endswith(extName) == True:  # 指定后缀名fullName = os.path.join(dir, file)  # 拼接名称fileGroup.append(fullName)  # 保存名称res = 0count = 0for file in fileGroup:if os.path.exists(file):count += 1print('[%04u] %s' % (count, file))return res, fileGroup#只处理 OrgDataFullDirNameExt原始文件数据
def Function_Option_Handler1():global OrgDataFullDirNameExtglobal CreatDataImageFullDirglobal CreatDataNameExtensionif os.path.isfile(OrgDataFullDirNameExt) == True:  # 原始数据文件存在Create_DataImage_DirFile(CreatDataImageFullDir, CreatDataNameExtension)  # 创建图片目录和统计文件成功File_OrgData_Handler(OrgDataFullDirNameExt, CreatDataImageFullDir, CreatDataStaFullDirNameExt)else:print(OrgDataFullDirNameExt, "OrgDat File No Exists......")#处理OrgDataDir目录下所有原始文件数据
def Function_Option_Handler2():global OrgDataFilesGroupglobal CreatDataExtensionglobal OrgDataDirglobal OrgDataExtensionres, OrgDataFilesGroup = Get_OrgData_FilesGroup(OrgDataDir, OrgDataExtension)if res == 0 and len(OrgDataFilesGroup) > 0:for orgFile in OrgDataFilesGroup:name = os.path.splitext(os.path.basename(orgFile))[0]  # 名称dir = os.path.join(CreatDataFatherDir, name)  # 拼接目录Create_DataImage_DirFile(dir, name + CreatDataExtension)File_OrgData_Handler(orgFile, dir, os.path.join(dir, name + CreatDataExtension))# 主函数入口
def main():global CreatDataFatherDirglobal OrgDataDirif Judg_BasicDir_Info(OrgDataDir, CreatDataFatherDir) == 0:  # 基本目录存在否Function_Option_Handler1()# Function_Option_Handler2()else:print("Basic Directory Creat Successful......")print("OrgData Handler Complete......")if __name__ == "__main__":main()

八、测试结果

原始数据
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/155721.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

哪个才是最适合你的 Web UI 自动化测试框架

最近&#xff0c;项目上出于系统性稳定性、减少测试工作量考虑&#xff0c;打算在 Web 前端引入 BDD。由于上一个项目写了一定的 Cucumber 代码&#xff08;BDD 测试框架之一&#xff09;&#xff0c;这个框架选型的责任便落到了我的肩膀上了。 在我们进行框架选型的时候&#…

字符数组基础知识

字符数组是存放字符数据的数组&#xff0c;其中每一个元素存放的值都是单个字符。 字符数组&#xff1a;由字符类型的元素组成&#xff0c;其定义与初始化方式&#xff0c;以及对数组元素的引用都与整数数组类似&#xff0c;代码示例 char c[5]{h,e,l,l,,o}; 注意&#xff1…

debian 修改IP 重启网络

vi /etc/network/interfaces /etc/init.d/networking restart

【SA8295P 源码分析 (三)】132 - GMSL2 协议分析 之 GPIO/SPI/I2C/UART 等通迅控制协议带宽消耗计算

【SA8295P 源码分析】132 - GMSL2 协议分析 之 GPIO/SPI/I2C/UART 等通迅控制协议带宽消耗计算 一、GPIO 透传带宽消耗计算二、SPI 通迅带宽消耗计算三、I2C 通迅带宽消耗计算四、UART 通迅带宽消耗计算系列文章汇总见:《【SA8295P 源码分析 (三)】Camera 模块 文章链接汇总 -…

如何做好前端单元测试?字节5年测试老司机是这样说的!

近几年&#xff0c;前端发展越来越迅猛&#xff0c;各类框架层出不穷&#xff0c;前端实现的业务逻辑也越来越复杂&#xff0c;前端单元测试也越来越受重视&#xff0c;包括百度在内的一些大厂在面试中也会问到单元测试相关的题目。那么前端应该如何做好单元测试&#xff1f; 什…

安全知识普及:了解端点检测与响应 (EDR)对企业的重要性

文章目录 EDR 的含义和定义EDR 是如何运作的&#xff1f;收集端点数据将数据发送到 EDR 平台分析数据标记可疑活动并做出响应保留数据以供日后使用 为什么 EDR 对企业至关重要大多数企业都有可能遭受各种网络攻击。有些攻击可以完全绕开企业的防御远程办公让员工缺乏足够的保护…

杨氏矩阵解法

每日一言 「 人生如逆旅&#xff0c;我亦是行人。 」--临江仙送钱穆父-苏轼题目 杨氏矩阵 有一个数字矩阵&#xff0c;矩阵的每行从左到右是递增的&#xff0c;矩阵从上到下是递增的&#xff0c;请编写程序在这样的矩阵中查找某个数字是否存在。 解法思路 法一&#xff1a;…

三字经||无聊数了下三字经的字数

三字经总字数去除标点后1416个 该文章无技术含量&#xff0c;仅三字经原文&#xff0c;学技术的同学可以止步了 三字经&#xff08;原文&#xff09; 【作者】王应麟 【朝代】南宋 人之初&#xff0c;性本善。性相近&#xff0c;习相远。 苟不教&#xff0c;性乃迁。教之道&a…

【SpringBoot】Redission 的使用与介绍

背景&#xff1a; 我想我们用到 Redisson 最多的场景一定是分布式锁&#xff0c;一个基础的分布式锁具有三个特性&#xff1a; 互斥&#xff1a;在分布式高并发的条件下&#xff0c;需要保证&#xff0c;同一时刻只有有一个线程获得锁&#xff0c;这是最基本的一点。 防止死…

基于知识问答的上下文学习中的代码风格11.20

基于知识问答的上下文学习中的代码风格 摘要1 引言2 相关工作3 方法3.1 概述3.2 元函数设计3.3 推理 4 实验4.1 实验设置4.2 实施细节4.3 主要结果 摘要 现有的基于知识的问题分类方法通常依赖于复杂的训练技术和模型框架&#xff0c;在实际应用中存在诸多局限性。最近&#x…

泵类设备常见的5种故障及监测方法

在各种工业领域中&#xff0c;泵是一种关键设备&#xff0c;用于输送液体或气体。然而&#xff0c;泵类设备常常会面临各种故障&#xff0c;这可能导致生产停顿和生产效率下降。为了及时监测并解决这些故障&#xff0c;设备状态监测系统成为一种重要的工具。本文将介绍泵类设备…

静态工具类中注入Bean及引用Nacos配置

目录 1.说明 2.示例 1.说明 在代码开发中&#xff0c;经常会存在调用第三方工具或者其他系统的场景&#xff0c;通常封装成一个工具类供service进行调用&#xff0c;便于后期的维护及代码复用。工具类中的属性及方法都被static修饰&#xff0c;在工具类中不能使用和service中…

Pytorch torch.norm函数详解用法

torch.norm参数定义 torch版本1.6 def norm(input, p"fro", dimNone, keepdimFalse, outNone, dtypeNone)input input (Tensor): the input tensor 输入为tensorp p (int, float, inf, -inf, fro, nuc, optional): the order of norm. Default: froThe following …

零代码编程:用ChatGPT将SRT字幕文件批量转为Word文本文档

一个文件夹中有多个srt视频字幕文件&#xff0c;srt文件里面有很多时间轴&#xff1a; 现在想将其批量转为word文档&#xff0c;去掉里面与字符无关的时间轴&#xff0c;在ChatGPT中输入提示词&#xff1a; 你是一个Python编程专家&#xff0c;要完成一个批量将SRT字幕文件转为…

js 数组中使用 push 报错

文章目录 问题分析 问题 代码如下&#xff0c;但报错如上&#xff0c;请分析上述代码错误原因 let arr [[160, 20], [179, 10], [-170, -20]]; let temp arr.unshift([1,1]); let tt temp.push([0,0])console.log(tt); // 输出新生成的数组分析 这段代码有几个错误&#x…

opencv-形态学处理

通过阈值化分割可以得到二值图&#xff0c;但往往会出现图像中物体形态不完整&#xff0c;变的残缺&#xff0c;可以通过形态学处理&#xff0c;使其变得丰满&#xff0c;或者去除掉多余的像素。常用的形态学处理算法包括&#xff1a;腐蚀&#xff0c;膨胀&#xff0c;开运算&a…

CDN加速在目前网络安全里的重要性

在当今数字化时代&#xff0c;网络已经成为我们生活不可或缺的一部分。然而&#xff0c;随之而来的是网络安全的威胁不断增加&#xff0c;为了应对这一挑战&#xff0c;CDN&#xff08;内容分发网络&#xff09;的应用变得愈发重要。本文将从一个旁观者的角度分析当前的网络安全…

【设计模式】结构型设计模式

结构型设计模式 文章目录 结构型设计模式一、概述二、适配器模式&#xff08;Adapter Pattern&#xff09;2.1 类适配器模式2.2 对象适配器模式2.3 接口适配器模式2.4 小结 三、桥接模式&#xff08;Bridge Pattern&#xff09;四、装饰器模式&#xff08;Decorator Pattern&am…

基于ubuntu20.04安装ros系统搭配使用工业相机

基于ubuntu20.04安装ros系统搭配使用工业相机 1. ROS系统安装部署1.1更新镜像源1.1.1 备份源文件1.1.2 更新阿里源1.1.3 更新软件源 1.2 ros系统安装1.2.1 添加ros软件源1.2.2 添加秘钥1.2.3 更新软件源1.2.4 配置及更换最佳软件源1.2.5 ROS安装1.2.6 初始化rosdep1.2.7 设置环…