add a merge tail alt operation

This commit is contained in:
Nitload
2026-06-16 00:23:43 +08:00
parent 861b50575a
commit 61b4c6012d
2 changed files with 55 additions and 71 deletions
@@ -2,8 +2,8 @@
// -----------------------------------------------------------------------
// file="RegexInterpreter"
// Project: StgSharp
// AuthorGroup: Nitload
// Copyright (c) Nitload. All rights reserved.
// AuthorGroup: Nitload Space
// Copyright (c) Nitload Space. All rights reserved.
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
@@ -58,9 +58,7 @@ namespace StgSharp.RegularAnalysis.TextRegex
}
}
public static RegexInterpreter Analyze(
string regex
)
public static RegexInterpreter Analyze(string regex)
{
RegexInterpreter interpreter = new();
interpreter._source = regex;
@@ -166,8 +164,8 @@ namespace StgSharp.RegularAnalysis.TextRegex
)
{
// phase0: scan container and remove no parent nodes
_tree.AllNodes.RemoveWhere(node => node.Parent == null && node != _tree.Root);
TreeEnumerator<RegexAstNode, RegexElementLabel> enumerator = new TreeEnumerator<RegexAstNode, RegexElementLabel>(_tree.Root);
_ = _tree.AllNodes.RemoveWhere(node => node.Parent == null && node != _tree.Root);
TreeEnumerator<RegexAstNode, RegexElementLabel> enumerator = new(_tree.Root);
RegexAstNode current;
// phase1: ALT flatten
@@ -179,10 +177,30 @@ namespace StgSharp.RegularAnalysis.TextRegex
current = enumerator.Current;
if (current.EqualityTypeConvert == RegexElementLabel.ALT)
{
RegexAstNode union = FlattenAlt(current);
altNodes.Add(current);
current.Right = union;
current.Left = RegexAstNode.Empty;
if (current.Left.EqualityTypeConvert == RegexElementLabel.UNIT &&
current.Right.EqualityTypeConvert == RegexElementLabel.UNIT)
{
if (string.IsNullOrEmpty(current.Left.Value))
{
// TODO replace the alt node with a count node
/*
RegexAstNode parent = current.Parent;
parent.Next = new RegexAstNode();
/**/
} else if (string.IsNullOrEmpty(current.Right.Value))
{
// TODO replace the alt node with a count node
} else
{
// TODO replace the alt node with a charset node
}
} else
{
RegexAstNode union = FlattenAlt(current);
altNodes.Add(current);
current.Right = union;
current.Left = RegexAstNode.Empty;
}
} else if (current.EqualityTypeConvert == RegexElementLabel.CONCAT) {
RotateConcat(current);
}
@@ -221,14 +239,11 @@ namespace StgSharp.RegularAnalysis.TextRegex
}
}
private void ProcessOperator(
RegexAstNode op
)
private void ProcessOperator(RegexAstNode op)
{
if (op.EqualityTypeConvert == RegexElementLabel.CONCAT)
{
if (_stack.TryPopOperand(out RegexAstNode? _1) &&
_stack.TryPopOperand(out RegexAstNode? _2))
if (_stack.TryPopOperand(out RegexAstNode? _1) && _stack.TryPopOperand(out RegexAstNode? _2))
{
op.Left = _2;
op.Right = _1;
@@ -254,8 +269,7 @@ namespace StgSharp.RegularAnalysis.TextRegex
}
} else if (op.EqualityTypeConvert == RegexElementLabel.ALT)
{
if (_stack.TryPopOperand(out RegexAstNode? _1) &&
_stack.TryPopOperand(out RegexAstNode? _2))
if (_stack.TryPopOperand(out RegexAstNode? _1) && _stack.TryPopOperand(out RegexAstNode? _2))
{
op.Left = _2;
op.Right = _1;