Пример #1
0
 public ChainBasedGenerator(TLayout initialLayout, IGeneratorPlanner <TLayout, TNode> generatorPlanner, List <Chain <TNode> > chains, ILayoutEvolver <TLayout, TNode> layoutEvolver, ILayoutConverter <TLayout, TOutputLayout> layoutConverter)
 {
     this.initialLayout    = initialLayout;
     this.generatorPlanner = generatorPlanner;
     this.chains           = chains;
     this.layoutEvolver    = layoutEvolver;
     this.layoutConverter  = layoutConverter;
 }
        public IList <TOutputLayout> GetLayouts(TMapDescription mapDescription, int numberOfLayouts)
        {
            var graph = mapDescription.GetGraph();

            if (graph.VerticesCount < 2)
            {
                throw new ArgumentException("Given mapDescription must contain at least two nodes.", nameof(mapDescription));
            }

            if (!graphUtils.IsConnected(graph))
            {
                throw new ArgumentException("Given mapDescription must represent a connected graph.", nameof(mapDescription));
            }

            if (!graphUtils.IsPlanar(graph))
            {
                throw new ArgumentException("Given mapDescription must represent a planar graph.", nameof(mapDescription));
            }

            // Create instances and inject the random generator and the cancellation token if possible
            configurationSpaces = configurationSpacesCreator(mapDescription);
            TryInjectRandomAndCancellationToken(configurationSpaces);

            chainDecomposition = chainDecompositionCreator(mapDescription);
            TryInjectRandomAndCancellationToken(chainDecomposition);

            initialLayout = initialLayoutCreator(mapDescription);
            TryInjectRandomAndCancellationToken(initialLayout);

            generatorPlanner = generatorPlannerCreator(mapDescription);
            TryInjectRandomAndCancellationToken(generatorPlanner);

            layoutOperations = layoutOperationsCreator(mapDescription, configurationSpaces);
            TryInjectRandomAndCancellationToken(layoutOperations);

            layoutConverter = layoutConverterCreator(mapDescription, configurationSpaces);
            TryInjectRandomAndCancellationToken(layoutConverter);

            layoutEvolver = layoutEvolverCreator(mapDescription, layoutOperations);
            TryInjectRandomAndCancellationToken(layoutEvolver);

            // Restart stopwatch
            stopwatch.Restart();

            chains  = chainDecomposition.GetChains(graph);
            context = new GeneratorContext();

            RegisterEventHandlers();

            // TODO: handle number of layouts to be evolved - who should control that? generator or planner?
            // TODO: handle context.. this is ugly
            var layouts = generatorPlanner.Generate(initialLayout, numberOfLayouts, chains.Count,
                                                    (layout, chainNumber, numOfLayouts) => layoutEvolver.Evolve(AddChain(layout, chainNumber), chains[chainNumber], numOfLayouts), context);

            // Stop stopwatch and prepare benchmark info
            stopwatch.Stop();
            timeTotal    = stopwatch.ElapsedMilliseconds;
            layoutsCount = layouts.Count;

            // Reset cancellation token if it was already used
            if (CancellationToken.HasValue && CancellationToken.Value.IsCancellationRequested)
            {
                CancellationToken = null;
            }

            return(layouts.Select(x => layoutConverter.Convert(x, true)).ToList());
        }