From 94622f5796227fe6772887f171e17834cfe685bc Mon Sep 17 00:00:00 2001 From: jackfiled Date: Sun, 10 Mar 2024 11:22:19 +0800 Subject: [PATCH] add: LrState --- Canon.Core/GrammarParser/Expression.cs | 16 ++++++- Canon.Core/GrammarParser/LrState.cs | 66 ++++++++++++++++++++++++++ 2 files changed, 80 insertions(+), 2 deletions(-) create mode 100644 Canon.Core/GrammarParser/LrState.cs diff --git a/Canon.Core/GrammarParser/Expression.cs b/Canon.Core/GrammarParser/Expression.cs index 096163f..980f0ef 100644 --- a/Canon.Core/GrammarParser/Expression.cs +++ b/Canon.Core/GrammarParser/Expression.cs @@ -1,17 +1,29 @@ namespace Canon.Core.GrammarParser; /// -/// An expression in the LR, like 'program_struct -> ~program_head ; program_body.' -/// The '~' is the shift position now. +/// LR语法中的一个表达式,例如 'program_struct -> ~program_head ; program_body' +/// 其中'~'标识当前移进到达的位置 /// public class Expression : IEquatable { + /// + /// 表达式的左部 + /// public required NonTerminator Left { get; init; } + /// + /// 表达式的向前看字符串 + /// public required Terminator LookAhead { get; init; } + /// + /// 表达式的右部 + /// public required List Right { get; init; } + /// + /// 当前移进的位置 + /// public int Pos { get; set; } public bool Equals(Expression? other) diff --git a/Canon.Core/GrammarParser/LrState.cs b/Canon.Core/GrammarParser/LrState.cs new file mode 100644 index 0000000..b5ffb65 --- /dev/null +++ b/Canon.Core/GrammarParser/LrState.cs @@ -0,0 +1,66 @@ +namespace Canon.Core.GrammarParser; + +/// +/// LR语法中的一个项目集规范族 +/// 也就是自动机中的一个状态 +/// +public class LrState : IEquatable +{ + /// + /// 项目集规范族 + /// + public required HashSet Expressions { get; init; } + + /// + /// 自动机的迁移规则 + /// + public Dictionary Transformer { get; } = []; + + public bool Equals(LrState? other) + { + if (other is null) + { + return false; + } + + if (Expressions.Count != other.Expressions.Count) + { + return false; + } + + // 如果两个集合的大小相等,且一个是另一个的子集,那么两个集合相等。 + return Expressions.IsSubsetOf(other.Expressions); + } + + public override bool Equals(object? obj) + { + if (obj is not LrState other) + { + return false; + } + + return Equals(other); + } + + public override int GetHashCode() + { + int hash = 0; + + foreach (Expression expression in Expressions) + { + hash ^= expression.GetHashCode(); + } + + return hash; + } + + public static bool operator ==(LrState a, LrState b) + { + return a.Equals(b); + } + + public static bool operator !=(LrState a, LrState b) + { + return !a.Equals(b); + } +}