Example #1
0
        public StageMap(IDictionary <int, List <int> > stageMapUnordered, bool preprocessed)
        {
            OrderableDictionary <int, List <int> > stageMap = new OrderableDictionary <int, List <int> >(stageMapUnordered);

            stageMap.OrderBy(s => s.Key);
            MappedTargetsIndex = new Dictionary <int, List <int> >();
            this.stageMap      = !preprocessed && stageMap.Any() ? ReviseStageMap(stageMap, MappedTargetsIndex) : stageMap;
        }
Example #2
0
        private static OrderableDictionary <int, List <int> > ReviseStageMap(OrderableDictionary <int, List <int> > stageMap, Dictionary <int, List <int> > mappedTargetsIndex)
        {
            /*
             * Do some validation
             */
            Nullable <int> length = null;

            foreach (var kvp in stageMap)
            {
                var stageId = kvp.Key;
                var rows    = kvp.Value;
                if (length == null)
                {
                    length = rows.Count;
                }
                else if (length.Value != rows.Count)
                {
                    throw new ConversionException("Invalid stage map metadata - stageID " + stageId + " expected " + length.Value + " rows but had " + rows.Count);
                }
            }

            if (length == null)
            {
                throw new NullableException(nameof(length));
            }
            int nextFreeIndex = length.Value;                                                                                                                             //Next free index equals length, as per all 0-N arrays
            OrderableDictionary <int, List <int> > resultStageMap = new OrderableDictionary <int, List <int> >(stageMap.ToDictionary(m => m.Key, m => m.Value.ToList())); //Copy dictionary

            resultStageMap.OrderBy(s => s.Key);
            Dictionary <int, bool> targetsStateMap = new Dictionary <int, bool>();

            /*
             * Traverse through the map, and duplicate targets as needed
             */
            foreach (var stageMapLine in stageMap)
            {
                int        stageId     = stageMapLine.Key;
                List <int> row         = stageMapLine.Value;
                int        targetIndex = 0;
                foreach (int cell in row)
                {
                    if (cell != 0)
                    {
                        bool targetState;
                        if (targetsStateMap.TryGetValue(targetIndex, out targetState))
                        {
                            if (!targetState)
                            {
                                //We're changing the state from not used to used, in which case we need to do the duplication
                                mappedTargetsIndex.AddNewListIfNotContainsKeyAndAddValueToList(targetIndex, nextFreeIndex);
                                int fillInValue = 0;
                                foreach (var kvp2 in resultStageMap)
                                {
                                    var resultStageId = kvp2.Key;
                                    var resultRows    = kvp2.Value;
                                    //This stage id marks the start of the block, so we switch the fillin value
                                    if (resultStageId == stageId)
                                    {
                                        fillInValue = 1;
                                    }

                                    //Check if this stage id result is 0, if so - switch out the block
                                    if (stageMap[resultStageId][targetIndex] == 0)
                                    {
                                        fillInValue = 0;
                                    }

                                    resultRows.Add(fillInValue);

                                    /*
                                     * If we already started filling out, remove original target as it wont be used anymore
                                     */
                                    if (resultStageId >= stageId)
                                    {
                                        resultRows[targetIndex] = 0;
                                    }
                                }

                                ++nextFreeIndex; //Increase the index
                            }
                        }

                        //We mark that the target is now used, perhaps was already used in which case this operation
                        //is doing nothing
                        targetsStateMap[targetIndex] = true;
                    }
                    else
                    {
                        //We mark that the target state changed to false ( perhaps it was already false, in which case
                        //this operation is doing nothing
                        //If the target was not used before, then we just continue, as it"s still not used.
                        targetsStateMap.SetIfContainsKey(targetIndex, false);
                    }

                    ++targetIndex;
                }
            }

            return(resultStageMap);
        }