Пример #1
0
        public static void OnlinePack(List <Container> containers, List <Item> itemsToPack)
        {
            //TODO
            //*Determinar a ordem como os itens sao associados (Decidir melhor container, utilizando os TipoItemId)

            foreach (var container in containers)
            {
                var _itemsToPack = itemsToPack.Where(ip => ip.IsPacked == false).ToList();

                if (_itemsToPack.Count == 0)
                {
                    break;
                }

                AlgorithmPackingResult algorithmResult = new OnlineContainerPacking().OnlineRun(container, _itemsToPack);

                algorithmResult.PackedItems.ForEach(pi =>
                {
                    var item = itemsToPack.Find(i => i.ID == pi.ID);

                    if (item != null)
                    {
                        item.IsPacked    = pi.IsPacked;
                        item.ContainerId = container.ID;

                        item.CoordX = pi.CoordX;
                        item.CoordY = pi.CoordY;
                        item.CoordZ = pi.CoordZ;

                        item.PackDimX = pi.PackDimX;
                        item.PackDimY = pi.PackDimY;
                        item.PackDimZ = pi.PackDimZ;

                        item.EmpilhamentoDisponivel = pi.EmpilhamentoDisponivel;
                        item.ItensEmpilhados        = pi.ItensEmpilhados;
                        item.ItemBaseId             = pi.ItemBaseId;

                        container.Alterado = true;
                    }
                });
            }
        }
Пример #2
0
        /// <summary>
        /// Attempts to pack the specified containers with the specified items using the specified algorithms.
        /// </summary>
        /// <param name="containers">The list of containers to pack.</param>
        /// <param name="itemsToPack">The items to pack.</param>
        /// <param name="algorithmTypeIDs">The list of algorithm type IDs to use for packing.</param>
        /// <returns>A container packing result with lists of the packed and unpacked items.</returns>
        public static List <ContainerPackingResult> Pack(List <Container> containers, List <Item> itemsToPack, List <int> algorithmTypeIDs)
        {
            Object sync = new Object {
            };
            List <ContainerPackingResult> result = new List <ContainerPackingResult>();

            Parallel.ForEach(containers, container =>
            {
                ContainerPackingResult containerPackingResult = new ContainerPackingResult();
                containerPackingResult.ContainerID            = container.ID;

                Parallel.ForEach(algorithmTypeIDs, algorithmTypeID =>
                {
                    var jsonDefinition = new
                    {
                        Height = new Decimal(),
                        Length = new Decimal(),
                        Volume = new Decimal(),
                        Width  = new Decimal(),
                        Items  = new List <Item>()
                    };

                    var onlineContainerJsonSource = "{\"Height\":9.0,\"Length\":15.0,\"Volume\":1755.0,\"Width\":13.0,\"Items\":[{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":1,\"IsPacked\":true,\"Dim1\":3.0,\"Dim2\":3.0,\"Dim3\":3.0,\"CoordX\":0.0,\"CoordY\":0.0,\"CoordZ\":0.0,\"PackDimX\":3.0,\"PackDimY\":3.0,\"PackDimZ\":3.0,\"Volume\":27.000},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":1,\"IsPacked\":true,\"Dim1\":3.0,\"Dim2\":3.0,\"Dim3\":3.0,\"CoordX\":3.0,\"CoordY\":0.0,\"CoordZ\":0.0,\"PackDimX\":3.0,\"PackDimY\":3.0,\"PackDimZ\":3.0,\"Volume\":27.000},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":1,\"IsPacked\":true,\"Dim1\":3.0,\"Dim2\":3.0,\"Dim3\":3.0,\"CoordX\":6.0,\"CoordY\":0.0,\"CoordZ\":0.0,\"PackDimX\":3.0,\"PackDimY\":3.0,\"PackDimZ\":3.0,\"Volume\":27.000},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":9.0,\"CoordY\":0.0,\"CoordZ\":0.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":11.0,\"CoordY\":0.0,\"CoordZ\":0.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":13.0,\"CoordY\":0.0,\"CoordZ\":0.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":9.0,\"CoordY\":0.0,\"CoordZ\":2.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":11.0,\"CoordY\":0.0,\"CoordZ\":2.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":13.0,\"CoordY\":0.0,\"CoordZ\":2.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":7.0,\"CoordY\":0.0,\"CoordZ\":3.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0},{\"ID\":0,\"PesoMaximo\":0,\"Peso\":0,\"EmpilhamentoDisponivel\":true,\"ItensEmpilhados\":[],\"TipoDeItemId\":2,\"IsPacked\":true,\"Dim1\":2.0,\"Dim2\":2.0,\"Dim3\":2.0,\"CoordX\":5.0,\"CoordY\":0.0,\"CoordZ\":3.0,\"PackDimX\":2.0,\"PackDimY\":2.0,\"PackDimZ\":2.0,\"Volume\":8.0}]}";

                    var onlineContainerSource = JsonConvert.DeserializeAnonymousType(onlineContainerJsonSource, jsonDefinition);

                    // Until I rewrite the algorithm with no side effects, we need to clone the item list
                    // so the parallel updates don't interfere with each other.
                    List <Item> items = new List <Item>();

                    onlineContainerSource.Items.ForEach(item =>
                    {
                        item.Quantity = 1;
                        //item.IsPacked = false;
                        items.Add(item);

                        item.ItensEmpilhados.ForEach(itemEmpilhado => items.Add(itemEmpilhado));
                    });

                    itemsToPack.ForEach(item =>
                    {
                        for (int i = 0; i < item.Quantity; i++)
                        {
                            items.Add(new Item(item.ID, item.Dim1, item.Dim2, item.Dim3, 1, item.TipoDeItemId));
                        }
                    });

                    Stopwatch stopwatch = new Stopwatch();
                    stopwatch.Start();
                    //AlgorithmPackingResult algorithmResult = algorithm.Run(container, items);
                    AlgorithmPackingResult algorithmResult = new OnlineContainerPacking().OnlineRun(container, items);
                    stopwatch.Stop();

                    algorithmResult.PackTimeInMilliseconds = stopwatch.ElapsedMilliseconds;

                    decimal containerVolume    = container.Length * container.Width * container.Height;
                    decimal itemVolumePacked   = algorithmResult.PackedItems.Sum(i => i.Volume);
                    decimal itemVolumeUnpacked = algorithmResult.UnpackedItems.Sum(i => i.Volume);

                    algorithmResult.PercentContainerVolumePacked = Math.Round(itemVolumePacked / containerVolume * 100, 2);
                    algorithmResult.PercentItemVolumePacked      = Math.Round(itemVolumePacked / (itemVolumePacked + itemVolumeUnpacked) * 100, 2);

                    var onlineContainer = new
                    {
                        Height = container.Height,
                        Length = container.Length,
                        Volume = container.Volume,
                        Width  = container.Width,
                        Items  = algorithmResult.PackedItems
                    };

                    var onlineContainerJson = JsonConvert.SerializeObject(onlineContainer);

                    lock (sync)
                    {
                        containerPackingResult.AlgorithmPackingResults.Add(algorithmResult);
                    }
                });

                containerPackingResult.AlgorithmPackingResults = containerPackingResult.AlgorithmPackingResults.OrderBy(r => r.AlgorithmName).ToList();

                lock (sync)
                {
                    result.Add(containerPackingResult);
                }
            });

            return(result);
        }