Superpower 正在尝试构建TextParser<;字符串[]>;具有相同的打开/关闭/分隔符

Superpower 正在尝试构建TextParser<;字符串[]>;具有相同的打开/关闭/分隔符,superpower,Superpower,我正在用SuperPower库构建一个解析器 下面是我要分析的源输入示例: | ABC | xyz | 1 3 | ~~~~~~ | 第一个|是开口管 最后一个|是关闭管道 第二、第三和第四个|是分隔符 最终,我希望能够在解析过程中生成此结构: 新字符串[]{“ABC”、“xyz”、“13”、“~~~”} 我想我遇到的问题是,我的分隔符字符与我的ClosingPipe字符相同 我应该如何构建这个TextParser?以下是一些适合您的解析器: public static TextParse

我正在用SuperPower库构建一个解析器

下面是我要分析的源输入示例:

| ABC | xyz | 1 3 | ~~~~~~ |

  • 第一个
    |
    开口管
  • 最后一个
    |
    关闭管道
  • 第二、第三和第四个
    |
    是分隔符
  • 最终,我希望能够在解析过程中生成此结构:
新字符串[]{“ABC”、“xyz”、“13”、“~~~”}
我想我遇到的问题是,我的分隔符字符与我的
ClosingPipe
字符相同


我应该如何构建这个
TextParser

以下是一些适合您的解析器:

public static TextParser<char> Pipe =>
    from c in Character.EqualTo('|')
    select c;

public static TextParser<string> Content =>
    from c in Character.Except('|').Many()
    select new string(c);

public static TextParser<string[]> Parser =>
    from openingPipe in Pipe
    from content1 in Content
    from closingPipe in Pipe
    from contents in Content.ManyDelimitedBy(Pipe)
    select new[] { content1 }
        .Concat(contents.Take(contents.Length - 1)) // remove the empty string on the end
        .ToArray();
结果
应该是
{ABC”,“xyz”,“13”,“~~~”}

这个想法是先解析开始的管道,然后是内容,然后是结束的管道,然后由于(我假设)分隔符的其余部分可以更改,您可以使用Superpower的内置方法
ManyDelimitedBy
解析出尽可能多的由管道分隔的其他内容片段。但是,由于您的输入总是在末尾有一个管道,因此
ManyDelimitedBy
将在
contents
数组的末尾留下一个空字符串,我将在返回最终输出之前删除该字符串

编辑 下面是一种不用切掉空字符串的方法:

public static TextParser<string> ExtraContent =>
    from content in Content
    from pipe in Pipe
    select content;

public static TextParser<string[]> Parser2 =>
    from openingPipe in Pipe
    from content1 in Content
    from closingPipe in Pipe
    from contents in ExtraContent.Many()
    select new[] { content1 }.Concat(contents).ToArray();
publicstatictextparser ExtraContent=>
从内容到内容
从管道到管道
选择内容;
公共静态TextParser解析器2=>
从管道中打开管道
从Content中的content1
从管道中关闭管道
来自ExtraContent.Many()中的内容
选择new[]{content1}.Concat(contents.ToArray();

管道之间是否允许任何字符?如果是这样的话,那么管道将如何在分隔管道之间逃逸?不,管道之间不允许有管道,因此不需要逃逸。移除末端的空字符串:这是我想出的同一个方法,但我不喜欢删除空字符串。现在我感觉没那么糟了。你也可以在开始解析之前把它切掉:)
public static TextParser<string> ExtraContent =>
    from content in Content
    from pipe in Pipe
    select content;

public static TextParser<string[]> Parser2 =>
    from openingPipe in Pipe
    from content1 in Content
    from closingPipe in Pipe
    from contents in ExtraContent.Many()
    select new[] { content1 }.Concat(contents).ToArray();