从字符串中提取关键字并将其分配给C#中的属性

时间:2017-12-04 19:11:58

标签: c#

我需要将数据从MATLAB传输到C#软件。来自MATLAB的数据也应该可以离线编辑(即在MATLAB和C#软件之外)。为此,我的MATLAB代码将具有可读模式的数据打印到文本文件中。例如:

<L> pt: [0.001,2,3], spd: 100, cfg: fut, daq: on, id: [1,1] </L>
<L> pt: [0.002,3,4], cfg: nut, spd: 100, id: [1,1], daq: on</L>
<C> pt: [0.02,5,3], spd: 100, daq: on, id: [1,1] </C>
<L> pt: [1.002,3,4], spd: 100, daq: off</L>

在C#中,我想解析每一行,提取这些关键字并将它们分配给属性:

enum PathType { L, C}
class Path
{
    public PathType Type { get; set; }
    public float[] Pt { get; set; }
    public int Spd { get; set; }
    public string Cfg { get; set; }
    public bool Daq { get; set; }
    public int[] Id { get; set; }
}

所以对于第1行,我打算看到这样的东西:

var path = new Path {
    PathType = PathType.L,
    Pt = new []{ 0.001, 2, 3 },
    Spd = 100,
    Cfg = "fut",
    Daq = true,
    Id = new []{ 1, 1 }};
第4行

var path = new Path {
    PathType = PathType.L,
    Pt = new []{ 1.002, 3, 4 },
    Spd = 100,
    Cfg = null,
    Daq = false,
    Id = null;

由于关键字按不同顺序排列,可能不会出现在所有行中,因此我无法使用单个正则表达式来提取这些信息。我必须使用多个正则表达式来测试每一行:

    var typeReg = new Regex(@"<(\w+)>");
    var ptReg = new Regex(@"pt:\s+(?<open>\[)[^\[]*(?<close-open>\])(?(open))");
    var spdReg = new Regex(@"spd:\s+(\d+)");
    var cfgReg = new Regex(@"cfg:\s+(fut|nut)");
    var daqReg = new Regex(@"daq:\s+(on|off)");
    var idReg = new Regex(@"id:\s+(?<open>\[)[^\[]*(?<close-open>\])(?(open))");

这有效,但我想知道是否有更好的方法可以做到这一点?

我应该以不同的模式打印数据,例如:

L; pt: [0.001,2,3]; spd: 100; cfg: fut; daq: on; id: [1,1]

然后我可以用分隔符;拆分字符串,然后用x.StartWith('...')检查每个子字符串。但是这样,我觉得它不像当前模式那样可读。

我不想使用xml,因为它会使文本文件大于所需的大小。

1 个答案:

答案 0 :(得分:2)

我比较了JSON和XML,发现XML更好。我对XML格式的理解很差,并认为它会大大增加文件大小,这是错误的。

JSON实施

此方法需要NuGet包,Newtonsoft.Json。还有其他solutions不需要它。

MATLAB输出:

{"type":"L", "pt": "[0.001,2,3]", "spd": "100", "cfg": "fut", "daq": "on", "id": "[1,1]"}

用于解码JSON的C#代码非常简单:

using Newtonsoft.Json;
public void Dictionary<string,string> DecodeJson(script)
{
    return JsonConvert.DeserializeObject(script);
}

返回的对象是一个字典,由属性名称组成,即type,pt,spd等,作为键,属性值作为值。

解码100k的示例输出大约需要330毫秒。

XML实施

MATLAB输出:

<L pt='[0.001,2,3]' spd='100' cfg='fut' daq='on' id='[1,1]'  />

C#代码:

public void Dictionary<string,string> DecodeXml(script)
{    
    var xmlObj = new Dictionary<string, string>();
    using (var reader = XmlReader.Create(new StringReader(script)))
    {
        reader.Read();
        // add node name, i.e. xmlObj["type"] -> L
        xmlObj.Add("type",reader.Name);
        // add all attributes
        while (reader.MoveToNextAttribute())
        {
            xmlObj.Add(reader.Name, reader.Value);
        }
    }
    return xmlObj;
}

此方法返回与JSON方法相同的对象。

解码100k的示例输出大约需要180 ms。

<强>结论

xml实现的输入字符串比JSON实现的输入字符串短,因此文件较小。 XML代码的执行时间几乎比JSON代码快2倍。因此,XML是更好的选择。