使用Python将XML作为任务/群集读取到LabVIEW以配置DAQ

问题描述

我正在尝试加载XML文件,该文件将用于在LabVIEW中配置DAQ。

因此,当我查看选项时,

  1. 我的XML通道配置是动态的-表示一个XML可能有3个通道,另一个可能有100个以上通道。
  2. 对我来说,用Python解析xml并将数据作为结构/任务传递给LabVIEW会容易得多。

例如用于XML频道

<Channels>
        <Channel name="CH_PH1" enable="True" visible="False" virtual="False" units="A" physical_channel="PXI1Slot2/ai0" b_factor="0" m_factor="1033.221069" measurement_type="VOLTAGE" type="D" max_value="0.1" min_value="-0.1">
          <RollingAvg do_rolling_avg="False" rolling_avg_frame_sec="0" />
        </Channel>
        <Channel name="CH_PH2" enable="True" visible="False" virtual="False" units="A" physical_channel="PXI1Slot2/ai1" b_factor="0" m_factor="1073.772766" measurement_type="VOLTAGE" type="D" max_value="0.1" min_value="-0.1">
          <RollingAvg do_rolling_avg="False" rolling_avg_frame_sec="0" />
        </Channel>
        <Channel name="P_CH" enable="True" visible="False" virtual="True" units="V" formula="CH_PH1*CH_PH2" doTotalEnergy="False">
          <RollingAvg do_rolling_avg="False" rolling_avg_frame_sec="0" />
        </Channel>
        <Channel name="P_PH_Total" enable="True" visible="False" virtual="True" units="V" formula="CH_PH1+CH_PH2" doTotalEnergy="False">
          <RollingAvg do_rolling_avg="False" rolling_avg_frame_sec="0" />
        </Channel>
</Channels>

我在Python中解析xml的代码

def xml():
    import xml.etree.ElementTree as ET
    tree = ET.parse(r'C:\Users\LAB_PTG\Desktop\Cosmo_v0.93.6\nidaq.xml')
    root = tree.getroot()
    P={}
    C={}
    for Channel in root.iter('Channel'):
        z=(Channel.attrib)
        if z['virtual']=='False':
            P.update({z['name']:(z['physical_channel'],z['enable'],z['m_factor'],z['max_value'])})
        else:
            C.update({z['name']:(z['formula'])})
    print(P,C)

需要帮助:

  1. 如何在LabVIEW中执行代码
  2. 如何在LabVIEW中处理DICT?还是有更好的解决方案来传递数据?
  3. 使用paras数据动态配置DAQmx通道

我无法在LabVIEW中创建XML解析器,因为它会执行更多的硬编码并具有固定的结构。

我的目标是LV DAQmx继续采样示例,并将配置替换为解析的xml。

enter image description here

感谢每一个支持 阿萨夫·贝克

解决方法

在Labview中解析XML

在LV中解析XML有点棘手,但并不是那么困难。也许您可以尝试一下?

此代码循环遍历所有通道,提取属性namevirtual,并从其子级RollingAvg提取属性do_rolling_avg

enter image description here

也许,首先获取节点的所有属性/值的列表,然后对生成的数组进行处理会更方便:

enter image description here

现在,重要的是最后关闭所有引用,以免发生内存泄漏,这是快速又肮脏的操作。

此外,如果未找到内容,则搜索VI将引发错误。 (您的Python也会这样做)。如有必要,应添加一些错误处理。


如果您坚持使用Python

今天,有一个选项可以直接从LV运行Python。我不知道,我的LV是2017年的。 在那里,可以使用System Exec.vi在命令行上运行任何命令,并将其输出读回LV:

enter image description here

最后,Python打印的内容将作为字符串返回。 我将使用JSON,它可以轻松地将字典转换为JSON:

import json

a=[]
a.append({'name':'CH_PH1','virtual':False,'RollingAvgFrame':3.141})
a.append({'name':'CH_PH2','virtual':True,'RollingAvgFrame':42.0})
print(json.dumps(a))

输出:

[{"name": "CH_PH1","virtual": false,"RollingAvgFrame": 3.141},{"name": "CH_PH2","virtual": true,"RollingAvgFrame": 42.0}]

在LV中,根据JSON结构定义一个集群,并使用Unflatten from JSON VI进行填充。群集元素的名称必须与JSON代码中的名称匹配。

enter image description here

但是,JSON仅知道简单的数据类型。除非可以将时间打包为更简单的内容(例如包含时间戳的字符串),否则无法传输时间或任何其他更复杂的数据类型。