| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252 | using System.Collections.Generic;using System.Linq;namespace wms.service.Extensions.LayerPacking.model{    /// <summary>    /// 层配装箱约束条件    /// </summary>    public class LayerPackingConstraints    {        /// <summary>        /// 产品目标值        /// </summary>        public decimal P { get; set; }        /// <summary>        /// 产品偏差范围        /// </summary>        public decimal P1 { get; set; }        /// <summary>        /// 箱总扭转目标值        /// </summary>        private decimal? _x;        /// <summary>        /// 层总扭转目标值        /// </summary>        private decimal? _c;        /// <summary>        /// 箱总产品数        /// </summary>        private int _productsPerBox;        /// <summary>        /// 箱总产品数        /// </summary>        public int ProductsPerBox        {            get => _productsPerBox;            set            {                _productsPerBox = value;                // 重新计算相关值                _x = null;                _c = null;            }        }        /// <summary>        /// 层总产品数        /// </summary>        private const int PRODUCTS_PER_LAYER = 12;        /// <summary>        /// 层总产品数        /// </summary>        public int ProductsPerLayer => PRODUCTS_PER_LAYER;        /// <summary>        /// 箱总层数        /// </summary>        public int LayersPerBox => ProductsPerBox / PRODUCTS_PER_LAYER;        /// <summary>        /// 箱总扭转目标值        /// </summary>        public decimal X        {            get => _x ?? P * ProductsPerBox;            set => _x = value;        }        /// <summary>        /// 箱总扭转目标偏差范围        /// </summary>        public decimal X1 { get; set; }        /// <summary>        /// 层总扭转目标值        /// </summary>        public decimal C        {            get => _c ?? P * PRODUCTS_PER_LAYER;            set => _c = value;        }        /// <summary>        /// 层总扭转目标偏差范围        /// </summary>        public decimal C1 { get; set; }        /// <summary>        /// 最大焊点盘数        /// </summary>        public int SolderMaxCount { get; set; }        /// <summary>        /// 最大焊点数        /// </summary>        public int PerSolderMaxCount { get; set; }        /// <summary>        /// 最小产品扭转目标值        /// </summary>        public decimal MinProductValue => P - P1;        /// <summary>        /// 最大产品扭转目标值        /// </summary>        public decimal MaxProductValue => P + P1;        /// <summary>        /// 是产品最小扭转目标值        /// </summary>        public bool IsAtMinTarget { get; private set; }        /// <summary>        /// 是产品最大扭转目标值        /// </summary>        public bool IsAtMaxTarget { get; private set; }        /// <summary>        /// 最小箱总目标值        /// </summary>        public decimal MinBoxTotal        {            get            {                if (X == P - P1 * ProductsPerBox)                    return X;                if (X == P + P1 * ProductsPerBox)                    return X - X1;                return X - X1;            }        }        /// <summary>        /// 最大箱总目标值        /// </summary>        public decimal MaxBoxTotal        {            get            {                if (X == P + P1 * ProductsPerBox)                    return X;                if (X == P - P1 * ProductsPerBox)                    return X + X1;                return X + X1;            }        }        /// <summary>        /// 最小层总目标值        /// </summary>        public decimal MinLayerTotal        {            get            {                if (C == P - P1 * PRODUCTS_PER_LAYER)                    return C;                if (C == P + P1 * PRODUCTS_PER_LAYER)                    return C - C1;                return C - C1;            }        }        /// <summary>        /// 最大层总目标值        /// </summary>        public decimal MaxLayerTotal        {            get            {                if (C == P + P1 * PRODUCTS_PER_LAYER)                    return C;                if (C == P - P1 * PRODUCTS_PER_LAYER)                    return C + C1;                return C + C1;            }        }        /// <summary>        /// 更新箱层目标值        /// </summary>        /// <param name="products"></param>        public void UpdateTargetValues(List<LayerPackingProduct> products)        {            if (products == null || !products.Any()) return;            decimal avgValue = products.Average(p => p.TorsChkValue);            decimal effectiveProductTarget; // 有效产品目标值  --计算箱层目标值时使用的产品目标值            if (avgValue <= MinProductValue)            {                effectiveProductTarget = MinProductValue;                IsAtMinTarget = true;                IsAtMaxTarget = false;            }            else if (avgValue >= MaxProductValue)            {                effectiveProductTarget = MaxProductValue;                IsAtMinTarget = false;                IsAtMaxTarget = true;            }            else            {                effectiveProductTarget = avgValue;                IsAtMinTarget = false;                IsAtMaxTarget = false;            }            _x = effectiveProductTarget * ProductsPerBox;            _c = effectiveProductTarget * PRODUCTS_PER_LAYER;            X1 = P1 * ProductsPerBox;            C1 = P1 * PRODUCTS_PER_LAYER;        }        /// <summary>        /// 获取焊点在装箱中的约束方案        /// </summary>        /// <returns></returns>        public SolderConstraintType GetSolderConstraintType()        {            if (SolderMaxCount <= 0) return SolderConstraintType.NoConstraint;            else if (PerSolderMaxCount <= 0) return SolderConstraintType.OnlyProductCount;            else return SolderConstraintType.BothConstraints;        }    }    /// <summary>    /// 焊点约束条件    /// </summary>    public enum SolderConstraintType    {        /// <summary>        /// 无约束条件        /// </summary>        NoConstraint,        /// <summary>        /// 仅产品数        /// </summary>        OnlyProductCount,        /// <summary>        /// 同时满足产品数和焊点数        /// </summary>        BothConstraints    }}
 |