LDF文件详解

  • 一、摘要
    • 1.描述
    • 2.关键字
  • 二、为什么要了解LDF文件
  • 三、LDF文件构成
    • 1.版本
    • 2.波特率
    • 3.节点信息
    • 4.信号信息
    • 5.诊断信号信息
    • 6.报文消息
    • 7.诊断报文消息
    • 8.从节点信息
    • 9.调度表
    • 10.描述信息
    • 11.信号描述关联
  • 四、LDF文件解析
    • 1.解析版本
    • 2.解析节点信息
    • 3.解析调度表
    • 4.解析报文消息
    • 5.解析诊断报文消息
    • 6.解析信号信息
    • 7.解析诊断信号信息
    • 8.解析信号描述关联
    • 9.解析描述信息
  • 五、MatrixCreat工具
  • 六、其他
  • 七、参考

一、摘要

1.描述

本文主要描述的是汽车行业中LDF文件的格式,如何去解析它,如何通过文本编辑器去修改它,了解LDF文件之前如果不懂LDF的请去查看我之前的博客。

2.关键字

LDF,LDF解析,LDF数据库,LDF文件,C#解析LDF文件。

二、为什么要了解LDF文件

LDF文件在汽车行业应用十分广泛,如果编辑LDF文件我们都使用Vector工具DF Explorer Pro或者LDFEditor去编辑,那效率将会是十分的低下,当我们了解了LDF文件的构成后,我们可以通过其他方式进行解析,可以大大的提高工作的效率,我们可以通过记事本或者其他工具打开LDF文件。

三、LDF文件构成

1.版本

关键字:LIN_protocol_version
格式:LIN_protocol_version = “version”;
格式中的version就是版本信息,版本信息可以为空,但是不能省略""符。
例如:LIN_protocol_version = “2.1”;代表版本号为V2.1。

2.波特率

关键字:LIN_speed
格式:LIN_speed = baudrate;
格式中的baudrate就是波特率。
例如:LIN_speed = 19.2 kbps;;代表波特率为19200。

3.节点信息

关键字:Nodes
格式:Nodes {
        Master: name1 jitter ms, timebase ms ;
        Slaves: name2,name3…;
      }

name1:主节点名称。
jitter:偏移是指一帧报文实际开始发送的时刻与帧时隙起点的时间差。
timebase:时间基数
name2,name3…:代表接收节点名称。
例如:Nodes {
        Master: GW_BCM, 1 ms, 0 ms ;
        Slaves: LIN_RLS,Tellus_Node;
      }
代表主节点名称为BCM,偏移为1ms,时间基数为0ms,从节点名称为LIN_RLS和Tellus_Node。

4.信号信息

关键字:Signals
格式:Signals {
        Signal_Name: Bit_Length, Signal_Init_Value, name1, name2… ;
        …;
      }

Signal_Name:信号名称,命名规则和C语言变量相同。
Bit_Length:信号的长度,范围为1-64。
Signal_Init_Value:信号初始值。
name1,name2…:代表接收节点名称。
例如:Signals {
        BCM_WiperRunning: 1, 0, GW_BCM, LIN_RLS ;
        RLS_MessageCounter: 4, 0, LIN_RLS, GW_BCM;
      }
代表信号名称为BCM_WiperRunning的长度为1,初始值为0,接收节点有GW_BCM, LIN_RLS;
信号名称为RLS_MessageCounter的长度为4,初始值为0,接收节点有LIN_RLS, GW_BCM;

5.诊断信号信息

关键字:Diagnostic_signals
格式:Diagnostic_signals{
        Signal_Name: Bit_Length, Signal_Init_Value ;
        …;
      }

Msg_ID:报文标识符,十进制表示。
Msg_Name:报文名称,命名规则和C语言变量相同。
Msg_Length :报文长度,长度范围为0-8。
例如:Diagnostic_signals{
        MasterReqB0: 8, 0 ;
        MasterReqB1: 8, 0 ;
        MasterReqB2: 8, 0 ;
        MasterReqB3: 8, 0 ;
        MasterReqB4: 8, 0 ;
        MasterReqB5: 8, 0 ;
        MasterReqB6: 8, 0 ;
        MasterReqB7: 8, 0 ;
        SlaveRespB0: 8, 0 ;
        SlaveRespB1: 8, 0 ;
        SlaveRespB2: 8, 0 ;
        SlaveRespB3: 8, 0 ;
        SlaveRespB4: 8, 0 ;
        SlaveRespB5: 8, 0 ;
        SlaveRespB6: 8, 0 ;
        SlaveRespB7: 8, 0 ;
      }
诊断报文一般自动生成的格式基本不变,也可以做一定名字调整等。

6.报文消息

关键字:Frames
格式:Frames {
        Msg_Name: Msg_ID, Msg_Transmitter, Msg_Length {
          Signal_Name, Start_Bit;
          …;
        };
        …;
      }

Msg_Name:报文名称,命名规则和C语言变量相同。
Msg_ID:报文标识符,十进制或者十六进制表示。
Msg_Transmitter:发送节点。
Msg_Length :报文长度,长度范围为0-8。
Signal_Name:信号名称,命名规则和C语言变量相同。
Start_Bit:信号的起始位,范围为0-63。
例如:Frames {
        BCM_data: 21, GW_BCM, 8{
          BCM_WiperRunning, 23;
        }
        RLS_data: 13, LIN_RLS, 8{
          RLS_MessageCounter, 0;
        }
      }
代表报文名称BCM_data的ID为0x15,长度为8,发送节点为GW_BCM,包含信号名称为BCM_WiperRunning,该信号起始位为23;
报文名称RLS_data的ID为0x0D,长度为8,发送节点为LIN_RLS,包含信号名称为RLS_MessageCounter,该信号起始位为0;

7.诊断报文消息

关键字:Diagnostic_frames
格式:Diagnostic_frames {
        MasterReq: Msg_ID{
          Signal_Name, Start_Bit;
          …;
        };
        SlaveResp: Msg_ID{
          Signal_Name, Start_Bit;
          …;
        };
      }

Msg_ID:报文标识符,十进制或者十六进制表示。
Msg_Length :报文长度,长度范围为0-8。
Signal_Name:信号名称,命名规则和C语言变量相同。
Start_Bit:信号的起始位,范围为0-63。
例如:Diagnostic_frames {
        MasterReq: 0x3c {
          MasterReqB0, 0;
          MasterReqB1, 8;
          MasterReqB2, 16;
          MasterReqB3, 24
          MasterReqB4, 32;
          MasterReqB5, 40;
          MasterReqB6, 48;
          MasterReqB7, 56;
        }
        SlaveResp: 0x3d {
          SlaveRespB0, 0;
          SlaveRespB1, 8;
          SlaveRespB2, 16;
          SlaveRespB3, 24
          SlaveRespB4, 32;
          SlaveRespB5, 40;
          SlaveRespB6, 48;
          SlaveRespB7, 56;
        }
      }

8.从节点信息

  • 关键字:Node_attributes
    格式:BA_DEF_ Object AttributeName ValueType Min Max;”
    Object:注解的对象类型,可以是节点“BU_”、报文“BO_”、消息”SG_”、网络节点” ”(用空格表示)。
    AttributeName: 自定义属性名称,命名规则和C语言变量相同。
    ValueType:属性值的类型,可以是整型、字符串、浮点型、枚举类型等。
    Min:属性值的最小值(字符串类型没有此项)。
    Min:属性值的最大值(字符串类型没有此项)。
    例如:BA_DEF_ “ECU” STRING ;代表自定义网络节点属性名称为ECU,类型为字符串型。
    BA_DEF_ BO_ “MsgCycleTime” INT 0 1000;代表自定义报文属性名称为MsgCycleTime,类型为整型,取值范围为0-1000。

9.调度表

  • 关键字:Node_attributes
    格式:BA_DEF_ Object AttributeName ValueType Min Max;”
    Object:注解的对象类型,可以是节点“BU_”、报文“BO_”、消息”SG_”、网络节点” ”(用空格表示)。
    AttributeName: 自定义属性名称,命名规则和C语言变量相同。
    ValueType:属性值的类型,可以是整型、字符串、浮点型、枚举类型等。
    Min:属性值的最小值(字符串类型没有此项)。
    Min:属性值的最大值(字符串类型没有此项)。
    例如:BA_DEF_ “ECU” STRING ;代表自定义网络节点属性名称为ECU,类型为字符串型。
    BA_DEF_ BO_ “MsgCycleTime” INT 0 1000;代表自定义报文属性名称为MsgCycleTime,类型为整型,取值范围为0-1000。

10.描述信息

关键字:Signal_encoding_types
格式:Signal_encoding_types {
        Signal_Encoding{
          physical_value, Min, Max, Factor, Offset,“Unit” ;
          logical_value, N, “DefineN;
          …;
        };
        …;
      }

Signal_Encoding:信号描述定义名称,命名规则和C语言变量相同。
N:定义的数值表内容。
Min:属性值的最小值(十进制)。
Min:属性值的最大值(十进制)。
Factor:精度。
Offset:偏移量,Factor和Offset这两个值于该信号的原始值与物理值之间的转换,转换如下:物理值=原始值*因子+偏移量。
DefineN:数值表内容对应该信号的有效值分别用什么符号表示。
Unit:信号的单位,为字符串类型,可以省略,省略时“,”也要省略。
例如:Signal_encoding_types{
        BCM_AMP_Driver_Encoding {
          physical_value, 0, 7, 1, 0 ;
          logical_value, 0, “No input” ;
          logical_value, 1, “Manual Up” ;
          logical_value, 2, “Manual Down” ;
        }
      }
代表描述信号名称为BCM_AMP_Driver_Encoding 的最小值为0,最大值为7,精度为1,偏移量为0,定义0x00表示为"No input" ,0x01表示为"Manual Up" ,0x02表示为"Manual Down" 。

11.信号描述关联

关键字:Signal_representation
格式:Signal_representation {
        Signal_Encoding: Signal_Name1, Signal_Name2…;
        …
      }

Signal_Encoding:信号描述定义名称,命名规则和C语言变量相同。
Signal_Name1,Signal_Name2…:信号定义名称,命名规则和C语言变量相同。
例如:Signal_representation {
        BCM_AMP_Driver_Encoding: BCM_AMP_Driver ;
        BCM_DRV_SWITCH_COOL_Encoding: BCM_DRV_SWITCH_COOL ;
      }
代表信号名称为BCM_AMP_Driver 的信号定义是BCM_AMP_Driver_Encoding的内容;
BCM_DRV_SWITCH_COOL_Encoding的信号定义是BCM_DRV_SWITCH_COOL 的内容。

四、LDF文件解析

通过以上描述,我相信各位对LDF文件的结构有一定的了解,但是我们如何去解析呢,很多人第一时间想到的应该是按行解析,其实LDF文件有许多容错处理,单纯按行解析我们会错过许多细节部分,例如下图其实也没有出错,如果按行解析的话报文就解析不到了。还有很多类似的容错处理在里面,所以单纯按行解析是不行的,并且有的时候也是不能通过空格来分开数据的,比如带有“”的前后是可以不追加空格的。

经过好久的挣扎,查询资料,终于在一个博客的找到了一种解析的方式,通过正则表达式去解析,当然他其实是按行解析,其实会丢掉一些数据,我将方法进行了一些简单的优化,先读取整个文件到字符串,把多行空格转换成一行空格,然后把换行符转换成空格符,然后进行查找,然后按照标准进行拆分。我这边解析的主要使用的C#语言,因为C#语言对字符串有友好的操作,我将部分代码粘贴如下,方便大家参考学习。

1.解析版本

       /**********************************************////<summary>///Name    :AnalysisVersion///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisVersion(MsgInfo_Type msgInfo, string data){string pattern = "LIN_protocol_version([ ]*)(=)([ ]*)\"((([^\"\\s])|([\\s\\u4e00-\\u9fa5]))*)\"([ ]*);";MatchCollection matchs = Regex.Matches(data, pattern);foreach (Match match in matchs){if (matchs.Count == 1){string[] array = match.Value.Split(new string[] { @"""" }, StringSplitOptions.RemoveEmptyEntries);if (array.Length >= 2) { msgInfo.version = array[1]; }return true;}}return true;}

2.解析节点信息

       /**********************************************////<summary>///Name    :AnalysisNodes///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisNodes(MsgInfo_Type msgInfo, string data){string pattern = "(Nodes[ ]*){[^{}]*}";foreach (Match match in Regex.Matches(data, pattern)){string masterPattern = "(Master[ ]*):([ ]*\\w+[ ]*),([ ]*(\\.|\\w|[ ])+[ ]*),([ ]*(\\.|\\w|[ ])+[ ]*);";foreach (Match masterMatch in Regex.Matches(match.Value, masterPattern)){string[] array = masterMatch.Value.Split(new string[] { " ", ":", ",", ";" }, StringSplitOptions.RemoveEmptyEntries);msgInfo.master = array[1];}string slavesPattern = "(Slaves[ ]*):([ ]*\\w+[ ]*)(,[ ]*\\w+[ ]*)*;";foreach (Match slavesMatch in Regex.Matches(match.Value, slavesPattern)){string[] array = slavesMatch.Value.Split(new string[] { " ", ":", ",", ";" }, StringSplitOptions.RemoveEmptyEntries);for (int i = 0; i < array.Length - 1; i++) { msgInfo.slaves.Add(array[i + 1]); }}}return true;}

3.解析调度表

       /**********************************************////<summary>///Name    :AnalysisScheduleTables///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisScheduleTables(MsgInfo_Type msgInfo, string data){string pattern = "(Schedule_tables[ ]*){(([^{}]*{[^{}]*})*)[ ]*}";foreach (Match match in Regex.Matches(data, pattern)){string eachPattern = "(\\w+[ ]*){((([ ]*\\w+[ ]+)delay([ ]+(\\d)+[ ]*(\\w)+[ ]*;[ ]*)))*}";foreach (Match eachMatch in Regex.Matches(match.Value, eachPattern)){string[] array = eachMatch.Value.Split(new string[] { " ", "{", "}", ";", "delay" }, StringSplitOptions.RemoveEmptyEntries);ScheduleInfoModel schedule = new ScheduleInfoModel { Name = array[0] };for (int i = 0; i < array.Length / 3; i++) { schedule.SlotInfos.Add(new SlotInfoModel() { Name = array[(3 * i) + 1], Delay = CommonLib.ToInt(array[(3 * i) + 2]) }); }msgInfo.schedules.Add(schedule);}}return true;}

4.解析报文消息

       /**********************************************////<summary>///Name    :AnalysisFrames///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisFrames(List<Message_Type> messages, string data){string pattern = "(Frames[ ]*){(([^{}]*{[^{}]*})*)[ ]*}";foreach (Match match in Regex.Matches(data, pattern)){string eachPattern = "(\\w+[ ]*):([ ]*\\w+[ ]*),([ ]*\\w+[ ]*),([ ]*\\d+[ ]*){(([ ]*)|(((([ ]*\\w+[ ]*),([ ]*\\d+[ ]*);[ ]*))+))}";foreach (Match eachMatch in Regex.Matches(match.Value, eachPattern)){Message_Type message = null;string messagePattern = "(\\w+[ ]*):([ ]*\\w+[ ]*),([ ]*\\w+[ ]*),([ ]*\\d+[ ]*)";foreach (Match messageMatch in Regex.Matches(eachMatch.Value, messagePattern)){string[] array = messageMatch.Value.Split(new string[] { " ", ",", ":" }, StringSplitOptions.RemoveEmptyEntries);uint? id = CommonLib.ToDec(array[1]);if (id == null) { continue; }message = FindMessage(messages, (uint)id);if (message == null){message = new Message_Type();messages.Add(message);}message.name = CommonLib.ToVar(array[0]);message.id = id;message.transmitter = CommonLib.ToStr(array[2]);message.length = CommonLib.ToInt(array[3]);message.sendType = SendTypeEnum.UF.ToString();message.checksumMode = ChecksumModeEnum.ENHANCED;}string signalPattern = "(\\w+[ ]*),([ ]*\\d+[ ]*);";foreach (Match signalMatch in Regex.Matches(eachMatch.Value, signalPattern)){string[] array = signalMatch.Value.Split(new string[] { " ", ",", ";" }, StringSplitOptions.RemoveEmptyEntries);message.signals.Add(new Signal_Type{name = CommonLib.ToStr(array[0]),startBit = CommonLib.ToInt(array[1]),byteOrder = ByteOrderEnum.INTEL,dataType = DataTypeEnum.UNSIGNED,factor = 1.0,offset = 0.0});}}}return true;}

5.解析诊断报文消息

       /**********************************************////<summary>///Name    :AnalysisDiagnosticFrames///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisDiagnosticFrames(List<Message_Type> messages, string data){string pattern = "(Diagnostic_frames[ ]*){(([^{}]*{[^{}]*})*)[ ]*}";foreach (Match match in Regex.Matches(data, pattern)){string eachPattern = "(\\w+[ ]*):([ ]*\\w+[ ]*){((([ ]*\\w+[ ]*),([ ]*\\d+[ ]*);[ ]*)*)}";foreach (Match eachMatch in Regex.Matches(match.Value, eachPattern)){Message_Type message = null;string messagePattern = "(\\w+[ ]*):([ ]*\\w+)";foreach (Match messageMatch in Regex.Matches(eachMatch.Value, messagePattern)){string[] array = messageMatch.Value.Split(new string[] { " ", ":" }, StringSplitOptions.RemoveEmptyEntries);uint? id = CommonLib.ToDec(array[1]);if (id == null) { continue; }message = FindMessage(messages, (uint)id);if (message == null){message = new Message_Type();messages.Add(message);}message.name = CommonLib.ToVar(array[0]);message.id = id;message.transmitter = null;message.length = 8;message.sendType = SendTypeEnum.DF.ToString();message.checksumMode = ChecksumModeEnum.CLASSIC;}string signalPattern = "(\\w+[ ]*),([ ]*\\d+[ ]*);";foreach (Match signalMatch in Regex.Matches(eachMatch.Value, signalPattern)){string[] array = signalMatch.Value.Split(new string[] { " ", ",", ";" }, StringSplitOptions.RemoveEmptyEntries);message.signals.Add(new Signal_Type{name = CommonLib.ToStr(array[0]),startBit = CommonLib.ToInt(array[1]),byteOrder = ByteOrderEnum.INTEL,dataType = DataTypeEnum.UNSIGNED,factor = 1.0,offset = 0.0});}}}return true;}

6.解析信号信息

       /**********************************************////<summary>///Name    :AnalysisSignals///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisSignals(List<Message_Type> messages, string data){string pattern = "(Signals[ ]*){[^{}]*}";foreach (Match match in Regex.Matches(data, pattern)){string signalPattern = "(\\w+[ ]*):([ ]*\\d+[ ]*),([ ]*([0][x])?\\d+[ ]*),([ ]*\\w+[ ]*(,[ ]*\\w+[ ]*)*);";foreach (Match signalMatch in Regex.Matches(match.Value, signalPattern)){string[] array = signalMatch.Value.Split(new string[] { " ", ":", ",", ";" }, StringSplitOptions.RemoveEmptyEntries);string signalName = CommonLib.ToStr(array[0]);foreach (Message_Type message in messages){foreach (Signal_Type signal in message.signals){if (signal.name == signalName){signal.length = CommonLib.ToInt(array[1]);signal.initValue = (int?)CommonLib.ToDec(array[2]);for (int i = 0; i < array.Length - 4; i++) { signal.receivers.Add(CommonLib.ToStr(array[i + 4])); }}}}}}return true;}

7.解析诊断信号信息

       /**********************************************////<summary>///Name    :AnalysisDiagnosticSignals///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisDiagnosticSignals(List<Message_Type> messages, string data){string pattern = "(Diagnostic_signals[ ]*){[^{}]*}";foreach (Match match in Regex.Matches(data, pattern)){string signalPattern = "(\\w+[ ]*):([ ]*\\d+[ ]*),([ ]*([0][x])?\\d+[ ]*);";foreach (Match signalMatch in Regex.Matches(match.Value, signalPattern)){string[] array = signalMatch.Value.Split(new string[] { " ", ":", ",", ";" }, StringSplitOptions.RemoveEmptyEntries);string signalName = CommonLib.ToStr(array[0]);foreach (Message_Type message in messages){foreach (Signal_Type signal in message.signals){if (signal.name == signalName){signal.length = CommonLib.ToInt(array[1]);signal.initValue = (int?)CommonLib.ToDec(array[2]);}}}}}return true;}

8.解析信号描述关联

       private static bool AnalysisSignalRepresentation(List<Message_Type> messages, string data){string pattern = "(Signal_representation[ ]*){[^{}]*}";foreach (Match match in Regex.Matches(data, pattern)){string signalPattern = "([ ]*\\w+[ ]*):([ ]*\\w+[ ]*(,[ ]*\\w+[ ]*)*);";foreach (Match signalMatch in Regex.Matches(match.Value, signalPattern)){string[] array = signalMatch.Value.Split(new string[] { " ", ",", ":", ";" }, StringSplitOptions.RemoveEmptyEntries);for (int i = 0; i < array.Length - 1; i++){string signalName = CommonLib.ToStr(array[i + 1]);foreach (Message_Type message in messages){foreach (Signal_Type signal in message.signals){if (signal.name == signalName){signal.encodingName = CommonLib.ToVar(array[0]);}}}}}}return true;}

9.解析描述信息

        /**********************************************////<summary>///Name    :AnalysisSignalEncodingTypes///Author  :WangHu///Function:***///Version :V1.0.0///Data    :2022.5.20///</summary>/**********************************************/private static bool AnalysisSignalEncodingTypes(List<Message_Type> messages, string data){string pattern = "(Signal_encoding_types[ ]*){(([^{}]*{[^{}]*})*)[ ]*}";foreach (Match match in Regex.Matches(data, pattern)){string eachPattern = "(\\w+[ ]*){((([ ]*physical_value[ ]*),([ ]*\\w+[ ]*),([ ]*\\w+[ ]*),((([ ]+)|)(-?\\d+(\\.\\d+)?)(([ ]+)|)),((([ ]+)|)(-?\\d+(\\.\\d+)?)(([ ]+)|))((,([ ]*)\"((([^\"\\s])|([\\s\\u4e00-\\u9fa5]))*)\")|)[ ]*;)+|[ ]*)((([ ]*logical_value[ ]*),([ ]*\\d+[ ]*),([ ]*\"((([^\"\\s])|([\\s\\u4e00-\\u9fa5]))*)\")[ ]*;[ ]*)+|[ ]*)}";foreach (Match eachMatch in Regex.Matches(match.Value, eachPattern)){string[] array = eachMatch.Value.Split(new string[] { " ", "{" }, StringSplitOptions.RemoveEmptyEntries);string encodingName = CommonLib.ToVar(array[0]);foreach (Message_Type message in messages){foreach (Signal_Type signal in message.signals){if (signal.encodingName == encodingName){try{string physicalPattern = "(physical_value[ ]*),([ ]*\\w+[ ]*),([ ]*\\w+[ ]*),((([ ]+)|)(-?\\d+(\\.\\d+)?)(([ ]+)|)),((([ ]+)|)(-?\\d+(\\.\\d+)?)(([ ]+)|))((,([ ]*)\"((([^\"\\s])|([\\s\\u4e00-\\u9fa5]))*)\")|)[ ]*;";foreach (Match physicalMatch in Regex.Matches(eachMatch.Value, physicalPattern)){string[] array1 = physicalMatch.Value.Replace(";", "").Split(new string[] { @"""" }, StringSplitOptions.None);string[] array2 = array1[0].Split(new string[] { " ", "," }, StringSplitOptions.RemoveEmptyEntries);signal.minValue = (int?)CommonLib.ToDec(array2[1]);signal.maxValue = (int?)CommonLib.ToDec(array2[2]);signal.factor = CommonLib.ToDouble(array2[3]);signal.offset = CommonLib.ToDouble(array2[4]);signal.unit = array1.Length >= 2 ? CommonLib.ToStr(array1[1]) : null;}string logicalPattern = "(logical_value[ ]*),([ ]*\\d+[ ]*),([ ]*\"((([^\"\\s])|([\\s\\u4e00-\\u9fa5]))*)\")[ ]*;";foreach (Match logicalMatch in Regex.Matches(eachMatch.Value, logicalPattern)){string[] array1 = logicalMatch.Value.Split(new string[] { @"""" }, StringSplitOptions.None);string[] array2 = array1[0].Split(new string[] { " ", "," }, StringSplitOptions.RemoveEmptyEntries);signal.valueDescriptions.Add(new ValueDescriptionInfoModel{Value = CommonLib.ToDec(array2[1]),Name = array1[1]});}}catch { continue; }}}}}}return true;}

五、MatrixCreat工具

这儿我只把链接放上,具体使用说明见后续章节。
LDF转Excel;LDF转位定义;Excel转LDF;Excel转位定义:https://download.csdn.net/download/weixin_44926112/86912538

六、其他

本文主要是讲解LDF文件的结构和如何解析LDF文件,有些地方可能会有描述性的错误,希望看到的朋友及时指出,我会及时更正错误,其他地方有些借鉴的描述,写此文章的目的是为了交流,非商业用途,欢迎私信讨论,感谢大家阅读。

七、参考

【1】:https://www.jianshu.com/p/8e1e47c4ee36

LDF转Excel;LDF转位定义;Excel转LDF;Excel转位定义;MatrixCreat(三)之LDF文件详解相关推荐

  1. python批量合并单元格_Python批量合并有合并单元格的Excel文件详解

    合并单元格 合并单元格相信大家都会,比如下面这段简单的代码就可以实现: app='Word' word=win32.gencache.EnsureDispatch('%s.Application' % ...

  2. 【python】解析Excel中使用xlrd库、xlwt库操作,使用xluils库修改Excel文件详解(三)...

    之前介绍了读和写excel,前两种都不是修改excel的,但是在实际的工作中,经常会遇到修改已经存在的Excel文件这种需求.xlrd中put_cell可以实现原表格上简单的写入,而xlwt直接生成新 ...

  3. python读取xls文件详解_python3解析excel文件

    一.需要的依赖 : xlrd 二.代码 #coding=utf-8 import xlrd ''' 读取Excel每个sheet的第一列和第二列的值,拼接成json串,写入文件 ''' def res ...

  4. python定义静态变量_对Pyhon实现静态变量全局变量的方法详解

    python不能像C++一样直接定义一个static变量或者通过extern来导入别的库的变量而实现数据共享,但是python的思想是通过模块化来解决这个问题,就是通过模块来实现全局变量. 首先新建一 ...

  5. decimal类型对象里面定义什么类型_MySQL中Decimal类型和Float Double的区别(详解)

    MySQL中存在float,double等非标准数据类型,也有decimal这种标准数据类型. 其区别在于,float,double等非标准类型,在DB中保存的是近似值,而Decimal则以字符串的形 ...

  6. java解析excel文件详解_java解析excel文件的方法

    建立工程前需要导入POI包.POI相关jar包下载地址:http://poi.apache.org/download.html 1.解析.xlsx后缀名的的EXCEL文件: package com.s ...

  7. python批量合并单元格的快捷键_关于Python批量合并有合并单元格的Excel文件详解...

    经常使用Excel的用户都知道,合并单元格的存在,这篇文章主要给大家介绍了关于利用Python如何批量合并有合并单元格的Excel文件的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具 ...

  8. python读写excel文件详解

    python读写excel我比较喜欢使用pandas工具,实在太方便了,这里首先介绍下pd.read_excel参数 import pandas as pd pd.read_excel(io,shee ...

  9. mib 文件中的 rowstatus 参数_k8s yaml格式的pod定义文件详解

    apiVersion: v1 #必选,版本号,例如v1kind: Pod #必选,Podmetadata: #必选,元数据 name: string #必选,Pod名称 namespace: stri ...

最新文章

  1. 交换机端口隔离技术应用
  2. 正则表达式调用“或”变量
  3. 南邮 Android 课程设计,南邮大四课程设计.doc
  4. PAZU 是4Fang 为配合“四方在线”软件于2004年开发的WEB打印控件,适用于各种WEB软件项目的打印。...
  5. Jenkins配置工具
  6. linux驱动头文件说明
  7. 路由器AP、路由、桥接模式有什么区别
  8. 【转】如何分析解决Android ANR
  9. 机器学习之PCA算法的人脸图像识别-平均脸的计算(详细操作步骤)
  10. [Shiro教程] Shiro 教程基于SSM(SpringMVC + Spring + Mybatis)
  11. 秃头警告之——使用mondo rescue备份linux系统ISO镜像的踩坑历程
  12. Linux环境下如何安装达梦数据库
  13. CHROME插件 by stormzhang
  14. 30 岁的码农人生 ——人生至暗时,你依然能窥见光明
  15. 创新案例分享 | 建设一体化智能化公共数据平台,赋能数字化改革
  16. 漫步微积分二十——微分和切线逼近
  17. [转载]S/4 HANA中的银行对账单
  18. 二分——切绳子(C++)
  19. 我国主要青少年编程竞赛简介
  20. 系统分析师-系统设计

热门文章

  1. zigbee zcl如何扩展cluster、扩展命令、扩展属性
  2. 音频质量客观评价指标
  3. 年后市场将反弹?服装人做好这些准备,才能赚到2023年第一桶金!
  4. 饲养员在给动物喂食时,给不同的动物喂不同的食物,而且在每次喂食时,动物都会发出欢快的叫声。例如,给小狗喂骨头,小狗会汪汪叫;给小猫喂食,小猫会喵喵叫。
  5. 网页粒子特效背景 Particleground.js 的简单引入
  6. 联想网御防火墙添加策略步骤
  7. 英飞凌代码生成_利用MATLAB-RTW的嵌入式代码自动生成与整合
  8. CSRF的攻击与防御
  9. 探究动态库函数的地址是在何时确定的
  10. My uBlock static filters