public static IEnumerable <Interval> FindIntervals(IntervalNode[] blocks, IntervalNode header)
        {
            var heads           = new HashSet <IntervalNode>();
            var intervalVisited = new HashSet <IntervalNode>();

            heads.Add(header);
            while (true)
            {
                var n = heads.Except(intervalVisited).FirstOrDefault();

                if (n == null)
                {
                    break;
                }
                intervalVisited.Add(n);
                var iofn = new HashSet <IntervalNode>();
                iofn.Add(n);
                while (true)
                {
                    var candidate = iofn.SelectMany(i => i.Successors.Intersect(blocks)).Distinct()
                                    .Except(iofn).FirstOrDefault(p => iofn.IsSupersetOf(p.Predecessors.Intersect(blocks)));
                    if (candidate == null)
                    {
                        break;
                    }
                    iofn.Add(candidate);
                }

                heads.UnionWith(blocks.Where(m =>
                                             !heads.Contains(m) && !iofn.Contains(m) &&
                                             m.Predecessors.Intersect(blocks).Any(p => iofn.Contains(p))));
                yield return(new Interval(n, iofn.ToArray()));
            }
        }
        public static IntervalNode[][] GetIntervalSequence(IntervalNode[] blocks, IntervalNode root)
        {
            var i1 = FindIntervals(blocks, root).ToArray();

            var intervalNodes = i1.Select(interval => new IntervalNode(interval)).ToArray();

            foreach (var intervalNode in intervalNodes)
            {
                intervalNode.Predecessors.AddRange(intervalNode.Interval.Blocks
                                                   .SelectMany(b => b.Predecessors)
                                                   .Except(intervalNode.Interval.Blocks)
                                                   .Select(b => intervalNodes.First(i => i.Interval.Blocks.Contains(b)))
                                                   .Distinct());
                intervalNode.Successors.AddRange(intervalNode.Interval.Blocks
                                                 .SelectMany(b => b.Successors)
                                                 .Except(intervalNode.Interval.Blocks)
                                                 .Select(b => intervalNodes.First(i => i.Interval.Blocks.Contains(b)))
                                                 .Distinct());
            }

            if (intervalNodes.Length != 1)
            {
                return(GetIntervalSequence(intervalNodes, intervalNodes[0]).Prepend(intervalNodes).ToArray());
            }
            return(new[] { intervalNodes });
        }
Exemple #3
0
 public Interval(IntervalNode header, IntervalNode[] blocks)
 {
     Header = header;
     Blocks = blocks;
 }