Example #1
0
        public static void SetUpwardsLimits(SolvingNode[] toposortedNodes)
        {
            void HandleUpwardLimits(SolvingNode node)
            {
                for (var index = 0; index < node.Ancestors.Count; index++)
                {
                    var ancestor = node.Ancestors[index];
                    ancestor.State = SetUpwardsLimits(node, ancestor);
                }

                if (node.State is ICompositeType composite)
                {
                    foreach (var member in composite.Members)
                    {
                        HandleUpwardLimits(member);
                    }
                }
            }

            foreach (var node in toposortedNodes.Where(n => !n.MemberOf.Any()))
            {
                HandleUpwardLimits(node);
            }
        }
Example #2
0
        public static FinalizationResults FinalizeUp(SolvingNode[] toposortedNodes, SolvingNode[] outputNodes)
        {
            var typeVariables = new HashSet <SolvingNode>();
            var syntaxNodes   = new SolvingNode[toposortedNodes.Length];
            var namedNodes    = new List <SolvingNode>();

            void Finalize(SolvingNode node)
            {
                if (node.State is RefTo)
                {
                    var originalOne = node.GetNonReference();

                    if (originalOne != node)
                    {
                        Console.WriteLine($"\t{node.Name}->r");
                        node.State = new RefTo(originalOne);
                    }

                    if (originalOne.State is IType)
                    {
                        node.State = originalOne.State;
                        Console.WriteLine($"\t{node.Name}->s");
                    }
                }
                else if (node.State is ICompositeType composite)
                {
                    if (composite.Members.Any(m => m.State is RefTo))
                    {
                        node.State = composite.GetNonReferenced();
                        Console.WriteLine($"\t{node.Name}->ar");
                    }

                    foreach (var member in composite.Members)
                    {
                        Finalize(member);
                    }
                }
            }

            foreach (var node in toposortedNodes.Reverse())
            {
                Finalize(node);

                foreach (var member in node.GetAllLeafTypes())
                {
                    if (member.Type == SolvingNodeType.TypeVariable && member.State is Constrains)
                    {
                        if (!typeVariables.Contains(member))
                        {
                            typeVariables.Add(member);
                        }
                    }
                }

                if (node.Type == SolvingNodeType.Named)
                {
                    namedNodes.Add(node);
                }
                else if (node.Type == SolvingNodeType.SyntaxNode)
                {
                    syntaxNodes[int.Parse(node.Name)] = node;
                }
            }


            var outputTypes = outputNodes
                              .SelectMany(s => s.GetAllLeafTypes())
                              .Distinct()
                              .ToArray();
            var notSolved = toposortedNodes
                            .Where(t => t.State is Constrains)
                            .Except(outputTypes)
                            .ToArray();

            foreach (var node in notSolved)
            {
                node.State = ((Constrains)node.State).TrySolveOrNull() ?? node.State;
            }

            return(new FinalizationResults(typeVariables.ToArray(), namedNodes.ToArray(), syntaxNodes));
        }