From d63b83c2c745c1f8a140221c28c0e6dbe61d6110 Mon Sep 17 00:00:00 2001
From: ningshuxia <ningshuxia0927@outlook.com>
Date: 星期二, 30 四月 2024 17:47:17 +0800
Subject: [PATCH] 调度修改

---
 Schedule/IStation.Algorithm/Entity/ScheduleCombine.cs            |   28 
 Schedule/IStation.Client/Form1.cs                                |    2 
 Schedule/IStation.Algorithm/Schedule/SchedulingHelper - 复制(4).cs |  291 +++++++++
 Schedule/IStation.Algorithm/Schedule/SchedulingHelper - 复制(3).cs |  275 ++++++++
 Schedule/IStation.Algorithm/Schedule/SchedulingHelper - 复制(5).cs |  290 +++++++++
 Schedule/IStation.Algorithm/Schedule/SchedulingHelper.cs         |  347 ++++++----
 Schedule/IStation.Algorithm/Schedule/SchedulingHelper - 复制.cs    |  255 ++++++++
 Schedule/IStation.Algorithm/IStation.Algorithm.csproj            |    5 
 Schedule/IStation.Algorithm/Schedule/SchedulingHelper - 复制(2).cs |  288 +++++++++
 Schedule/IStation.Algorithm/Schedule/SchedulingAnaHelper.cs      |   34 
 Schedule/IStation.Algorithm/DAL/ScheduleConclusion.cs            |   25 
 Schedule/IStation.Algorithm/Entity/ScheduleConclusion.cs         |    5 
 12 files changed, 1,695 insertions(+), 150 deletions(-)

diff --git a/Schedule/IStation.Algorithm/DAL/ScheduleConclusion.cs b/Schedule/IStation.Algorithm/DAL/ScheduleConclusion.cs
index fb0e762..f1c8372 100644
--- a/Schedule/IStation.Algorithm/DAL/ScheduleConclusion.cs
+++ b/Schedule/IStation.Algorithm/DAL/ScheduleConclusion.cs
@@ -224,7 +224,29 @@
 
 
         /// <summary>
-        /// 澶ф壒閲忔彃鍏�
+        /// 鏌ヨ
+        /// </summary>
+        public List<Entity.ScheduleConclusion> GetList(string runFlag, double targetHead)
+        {
+            var tableName = GetTableName(runFlag);
+            using (SqlSugarClient db = Connection)
+            {
+                var sql = $"select count(*)  from sqlite_master where type = 'table' and name = '{tableName}';";
+                if (db.Ado.GetInt(sql) < 1)
+                {
+                    return default;
+                }
+                var list = db.Queryable<Entity.ScheduleConclusion>().AS(tableName)
+                      .Where(x => x.Head == targetHead)
+                      .OrderBy(x => x.Power)
+                      .ToList();
+                return list;
+            }
+
+        }
+
+        /// <summary>
+        /// 鏌ヨ
         /// </summary>
         public List<Entity.ScheduleConclusion> GetList(string runFlag, double targetFlow, double targetHead, int takeCount)
         {
@@ -243,7 +265,6 @@
                       .ToList();
                 return list;
             }
-
 
         }
 
diff --git a/Schedule/IStation.Algorithm/Entity/ScheduleCombine.cs b/Schedule/IStation.Algorithm/Entity/ScheduleCombine.cs
index 16b6bc6..798692e 100644
--- a/Schedule/IStation.Algorithm/Entity/ScheduleCombine.cs
+++ b/Schedule/IStation.Algorithm/Entity/ScheduleCombine.cs
@@ -19,6 +19,11 @@
             this.Pump3 = rhs.Pump3;
             this.CurveQH = rhs.CurveQH;
             this.CurveQP = rhs.CurveQP;
+
+            this.MinFlow = rhs.MinFlow;
+            this.MaxFlow = rhs.MaxFlow;
+            this.MaxHead = rhs.MaxHead;
+            this.MinHead = rhs.MinHead;
             this.AnaStatus = rhs.AnaStatus;
         }
 
@@ -31,8 +36,7 @@
 
         /// <summary>
         /// 杩愯鏍囧織
-        /// </summary> 
-        [SplitField]
+        /// </summary>  
         public string RunFlag { get; set; }
 
         /// <summary>
@@ -66,6 +70,26 @@
         public string CurveQP { get; set; }
 
         /// <summary>
+        /// 鏈�澶ф祦閲�
+        /// </summary>
+        public double MaxFlow { get; set; }
+
+        /// <summary>
+        /// 鏈�灏忔祦閲�
+        /// </summary>
+        public double MinFlow { get; set; }
+
+        /// <summary>
+        /// 鏈�澶ф壃绋�
+        /// </summary>
+        public double MaxHead { get; set; }
+
+        /// <summary>
+        /// 鏈�灏忔壃绋�
+        /// </summary>
+        public double MinHead { get; set; }
+
+        /// <summary>
         /// 鍒嗘瀽鐘舵��
         /// </summary>
         public bool AnaStatus { get; set; }
diff --git a/Schedule/IStation.Algorithm/Entity/ScheduleConclusion.cs b/Schedule/IStation.Algorithm/Entity/ScheduleConclusion.cs
index 13e5986..65a21ce 100644
--- a/Schedule/IStation.Algorithm/Entity/ScheduleConclusion.cs
+++ b/Schedule/IStation.Algorithm/Entity/ScheduleConclusion.cs
@@ -14,6 +14,7 @@
         {
             this.ID = rhs.ID;
             this.ScheduleCombineID = rhs.ScheduleCombineID;
+            this.RunFlag = rhs.RunFlag;
             this.Pump1 = rhs.Pump1;
             this.Pump2 = rhs.Pump2;
             this.Pump3 = rhs.Pump3;
@@ -50,10 +51,10 @@
 
         /// <summary>
         /// 杩愯鏍囧織
-        /// </summary>
-       // [SplitField]
+        /// </summary> 
         public string RunFlag { get; set; }
 
+
         /// <summary>
         /// 娉�1
         /// </summary>
diff --git a/Schedule/IStation.Algorithm/IStation.Algorithm.csproj b/Schedule/IStation.Algorithm/IStation.Algorithm.csproj
index 36d7d7a..381f4a8 100644
--- a/Schedule/IStation.Algorithm/IStation.Algorithm.csproj
+++ b/Schedule/IStation.Algorithm/IStation.Algorithm.csproj
@@ -35,6 +35,11 @@
 	  <Compile Remove="Schedule\SchedulingAnaHelper_v1.cs" />
 	  <Compile Remove="Schedule\SchedulingAnaHelper_v3.cs" />
 	  <Compile Remove="Schedule\SchedulingCombineAnaHelper - 澶嶅埗.cs" />
+	  <Compile Remove="Schedule\SchedulingHelper - 澶嶅埗%282%29.cs" />
+	  <Compile Remove="Schedule\SchedulingHelper - 澶嶅埗%283%29.cs" />
+	  <Compile Remove="Schedule\SchedulingHelper - 澶嶅埗%284%29.cs" />
+	  <Compile Remove="Schedule\SchedulingHelper - 澶嶅埗%285%29.cs" />
+	  <Compile Remove="Schedule\SchedulingHelper - 澶嶅埗.cs" />
 	</ItemGroup>
 
 	<ItemGroup>
diff --git a/Schedule/IStation.Algorithm/Schedule/SchedulingAnaHelper.cs b/Schedule/IStation.Algorithm/Schedule/SchedulingAnaHelper.cs
index 38a5f47..fa8d83e 100644
--- a/Schedule/IStation.Algorithm/Schedule/SchedulingAnaHelper.cs
+++ b/Schedule/IStation.Algorithm/Schedule/SchedulingAnaHelper.cs
@@ -195,6 +195,12 @@
                                     scheduleCombine.Pump1 = freItem.Frequency;
                                     scheduleCombine.CurveQH = freItem.CurveQH.ToJson();
                                     scheduleCombine.CurveQP = freItem.CurveQP.ToJson();
+
+                                    freItem.CurveQH.GetMinMaxPointY(out double maxHead, out double minHead);
+                                    scheduleCombine.MinFlow = freItem.CurveQH.Min;
+                                    scheduleCombine.MaxFlow = freItem.CurveQH.Max;
+                                    scheduleCombine.MaxHead = maxHead;
+                                    scheduleCombine.MinHead = minHead;
                                     scheduleCombine.AnaStatus = false;
                                     list.Add(scheduleCombine);
                                 }
@@ -239,8 +245,18 @@
                                         scheduleCombine.RunCount = pumpCount;
                                         scheduleCombine.Pump1 = freItem1.Frequency;
                                         scheduleCombine.Pump2 = freItem2.Frequency;
-                                        scheduleCombine.CurveQH = FitHelper.BuildCurveExpress(pointQH).ToJson();
-                                        scheduleCombine.CurveQP = FitHelper.BuildCurveExpress(pointQP).ToJson();
+
+                                        var curveQH = FitHelper.BuildCurveExpress(pointQH);
+                                        var curveQP = FitHelper.BuildCurveExpress(pointQP);
+
+                                        scheduleCombine.CurveQH = curveQH.ToJson();
+                                        scheduleCombine.CurveQP = curveQP.ToJson();
+
+                                        curveQH.GetMinMaxPointY(out double maxHead, out double minHead);
+                                        scheduleCombine.MinFlow = curveQH.Min;
+                                        scheduleCombine.MaxFlow = curveQH.Max;
+                                        scheduleCombine.MaxHead = maxHead;
+                                        scheduleCombine.MinHead = minHead;
                                         scheduleCombine.AnaStatus = false;
                                         list.Add(scheduleCombine);
                                     }
@@ -290,8 +306,18 @@
                                             scheduleCombine.Pump1 = freItem1.Frequency;
                                             scheduleCombine.Pump2 = freItem2.Frequency;
                                             scheduleCombine.Pump3 = freItem3.Frequency;
-                                            scheduleCombine.CurveQH = FitHelper.BuildCurveExpress(pointQH).ToJson();
-                                            scheduleCombine.CurveQP = FitHelper.BuildCurveExpress(pointQP).ToJson();
+
+                                            var curveQH = FitHelper.BuildCurveExpress(pointQH);
+                                            var curveQP = FitHelper.BuildCurveExpress(pointQP);
+
+                                            scheduleCombine.CurveQH = curveQH.ToJson();
+                                            scheduleCombine.CurveQP = curveQP.ToJson();
+
+                                            curveQH.GetMinMaxPointY(out double maxHead, out double minHead);
+                                            scheduleCombine.MinFlow = curveQH.Min;
+                                            scheduleCombine.MaxFlow = curveQH.Max;
+                                            scheduleCombine.MaxHead = maxHead;
+                                            scheduleCombine.MinHead = minHead;
                                             scheduleCombine.AnaStatus = false;
                                             list.Add(scheduleCombine);
                                         }
diff --git "a/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0502\051.cs" "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0502\051.cs"
new file mode 100644
index 0000000..8f29a13
--- /dev/null
+++ "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0502\051.cs"
@@ -0,0 +1,288 @@
+锘縩amespace IStation.Algorithm
+{
+
+    #region ViewModel
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class AnaItem
+    {
+        public AnaItem() { }
+        public string RunFlag { get; set; }
+        public int RunCount { get; set; }
+        public List<long> PumpIds { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+    }
+
+    #endregion
+
+    /// <summary>
+    /// 璋冨害鍒嗘瀽杈呭姪绫�
+    /// </summary>
+    public class SchedulingHelper
+    {
+        double _frequency_def = 50;
+        double _frequency_min = 25;
+        double _frequency_max = 50;
+        double _frequency_space = 0.1;//棰戠巼闂撮殧  
+
+        double _head_space = 0.1;//鎵▼闂撮殧
+
+        #region RunFlag
+        string _falgFrePumpTag = "B";
+        string _falgFixPumpTag = "G";
+        string _falgSpaceMark = "_";
+
+        string GetRunFlag(List<AnaPumpItem> pumpItems)
+        {
+            var tableName = string.Empty;
+            var count = pumpItems.Count;
+            pumpItems = pumpItems.OrderBy(p => p.ID).ToList();
+            for (int i = 0; i < count; i++)
+            {
+                var pumpItem = pumpItems[i];
+                tableName += GetRunFlag(pumpItem);
+                if ((i + 1) != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+        string GetRunFlag(AnaPumpItem pumpItem)
+        {
+            return (pumpItem.IsBp ? _falgFrePumpTag : _falgFixPumpTag) + pumpItem.ID;
+        }
+
+
+        string GetRunFlag(Dictionary<int, bool> dic)
+        {
+            var tableName = string.Empty;
+            var index = 0;
+            var count = dic.Count;
+            foreach (var item in dic)
+            {
+                tableName += GetRunFlag(item.Key, item.Value);
+                index++;
+                if (index != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+        string GetRunFlag(long id, bool isBp)
+        {
+            return (isBp ? _falgFrePumpTag : _falgFixPumpTag) + id;
+        }
+
+        string GetRunFlag(List<string> flags)
+        {
+            var tableName = string.Empty;
+            var count = flags.Count;
+            var index = 0;
+            foreach (var flag in flags)
+            {
+                tableName += flag;
+                index++;
+                if (index != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+        string GetRunFlag(List<int> flags)
+        {
+            var tableName = string.Empty;
+            var count = flags.Count;
+            var index = 0;
+            foreach (var flag in flags)
+            {
+                tableName += flag;
+                index++;
+                if (index != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+
+        #endregion
+
+        DAL.ScheduleCombine _dal = new DAL.ScheduleCombine();
+        DAL.ScheduleConclusion _dalScheduleConclusion = new DAL.ScheduleConclusion();
+        DAL.ScheduleAnaLog _dalAnaLog = new DAL.ScheduleAnaLog();
+
+
+        public class CurrentViewModel : Entity.ScheduleConclusion
+        {
+            public CurrentViewModel(Entity.ScheduleConclusion rhs) : base(rhs)
+            {
+                this.Flags = new List<int>();
+                var flags = rhs.RunFlag.Split('_');
+                foreach (var item in flags)
+                {
+                    if (int.TryParse(item.Substring(1), out int flag))
+                    {
+                        this.Flags.Add(flag);
+                    }
+
+                }
+            }
+            public List<int> Flags { get; set; }
+        }
+
+
+        public void Ana(List<Pump> pumps, double tagetFlow, double tagetHead, List<int> openPumpCombine)
+        {
+            var pumpIds = pumps.Select(x => x.ID);
+            var dic_pump = pumps.ToDictionary(x => x.ID, x => x.IsBp);
+
+
+            if (openPumpCombine != null && openPumpCombine.Any())
+            {
+                {
+                    var optimalConclusionList = new List<CurrentViewModel>();
+                    foreach (var pump in openPumpCombine)
+                    {
+                        var runFalg = GetRunFlag(pump, dic_pump[pump]);
+                        var list = _dalScheduleConclusion.GetList(runFalg, tagetHead, 1);
+                        if (list != null && list.Any())
+                        {
+                            var vmList = list.Select(x => new CurrentViewModel(x)).ToList();
+                            optimalConclusionList.AddRange(vmList);
+                        }
+                    }
+                    if (optimalConclusionList == null || !optimalConclusionList.Any())
+                    {
+                        return;
+                    }
+
+                    var optimalConclusionCombineList = PermutationAndCombination<CurrentViewModel>.GetCombination(optimalConclusionList.ToArray(), 4);
+                    var combines = new List<Combine>();
+                    foreach (var arr in optimalConclusionCombineList)
+                    {
+                        var falgs = arr.SelectMany(x => x.Flags).ToList();
+                        if (falgs.GroupBy(x => x).Where(x => x.Count() > 1).Count() > 0)
+                        {
+                            continue;
+                        }
+                        var combine = new Combine();
+                        combine.RunFlag = GetRunFlag(falgs);
+                        combine.Power = arr.Sum(x => x.Power);
+                        combine.Head = arr.Average(x => x.Head);
+                        combine.Flow = arr.Sum(x => x.Flow);
+                        combine.RunFlagList = falgs;
+                        combines.Add(combine);
+                    }
+
+                    var a = combines.OrderBy(x => x.Flow).ThenBy(x => x.Power).ToList();
+                }
+
+
+                {
+                    var allCombineList = PermutationAndCombination<int>.GetCombination(pumpIds.ToArray(), 2);
+                    var combineList = new List<List<int>>();
+                    foreach (var combine in allCombineList)
+                    {
+                        var pump1 = combine[0];
+                        var pump2 = combine[1];
+                        if (!openPumpCombine.Contains(pump1))
+                            continue;
+                        if (!openPumpCombine.Contains(pump2))
+                            continue;
+                        combineList.Add(combine.ToList());
+                    }
+                    if (combineList.Count < 1)
+                        return;
+
+                    var avgFlow = tagetFlow / 2;
+
+                    var optimalConclusionList = new List<CurrentViewModel>();
+                    foreach (var combine in combineList)
+                    {
+                        var dic = new Dictionary<int, bool>();
+                        foreach (var pump in combine)
+                        {
+                            if (dic_pump.ContainsKey(pump))
+                            {
+                                dic.Add(pump, dic_pump[pump]);
+                            }
+                        }
+                        var runFalg = GetRunFlag(dic);
+                        var list = _dalScheduleConclusion.GetList(runFalg, avgFlow, tagetHead, 5);
+                        if (list != null && list.Any())
+                        {
+                            var vmList = list.Select(x => new CurrentViewModel(x)).ToList();
+                            optimalConclusionList.AddRange(vmList);
+                        }
+                    }
+                    if (optimalConclusionList == null || !optimalConclusionList.Any())
+                    {
+                        return;
+                    }
+
+                    var optimalConclusionCombineList = PermutationAndCombination<CurrentViewModel>.GetCombination(optimalConclusionList.ToArray(), 2);
+                    var combines = new List<Combine>();
+                    foreach (var arr in optimalConclusionCombineList)
+                    {
+                        var falgs = arr.SelectMany(x => x.Flags).ToList();
+                        if (falgs.GroupBy(x => x).Where(x => x.Count() > 1).Count() > 0)
+                        {
+                            continue;
+                        }
+                        var combine = new Combine();
+                        combine.RunFlag = GetRunFlag(falgs);
+                        combine.Power = arr.Sum(x => x.Power);
+                        combine.Head = arr.Average(x => x.Head);
+                        combine.Flow = arr.Sum(x => x.Flow);
+                        combine.RunFlagList = falgs;
+                        combines.Add(combine);
+                    }
+
+                    var a = combines.OrderBy(x => x.Flow).ThenBy(x => x.Power).ToList();
+                }
+
+
+            }
+        }
+
+        private class Combine
+        {
+            public double Flow { get; set; }
+            public double Head { get; set; }
+            public double Power { get; set; }
+            public string RunFlag { get; set; }
+            public List<int> RunFlagList { get; set; }
+        }
+
+
+
+        /// <summary>
+        /// 鎻掑叆鍒嗘瀽鏃ュ織
+        /// </summary> 
+        private void InsertAnaLog(string info)
+        {
+            var entity = new Entity.ScheduleAnaLog(info);
+            _dalAnaLog.Insert(entity);
+        }
+
+
+        /// <summary>
+        /// 鍒ゆ柇琛ㄦ槸鍚﹀瓨鍦�
+        /// </summary>
+        public bool ExistTable(string runFlag)
+        {
+            return _dal.ExistTable(runFlag);
+        }
+
+    }
+}
diff --git "a/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0503\051.cs" "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0503\051.cs"
new file mode 100644
index 0000000..83edfb0
--- /dev/null
+++ "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0503\051.cs"
@@ -0,0 +1,275 @@
+锘縰sing IStation.Model;
+
+namespace IStation.Algorithm
+{
+
+    #region ViewModel
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class Combine
+    {
+        public Combine() { }
+        public List<int> PumpIds { get; set; }
+        public string RunFlag { get; set; }
+        public int RunCount { get; set; }
+        public double Frequency { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+        public double Power { get; set; }
+    }
+
+
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class OptimalCombine
+    {
+        public OptimalCombine() { }
+        public List<int> PumpIds { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+        public double Power { get; set; }
+        public List<Combine> Combines { get; set; }
+    }
+
+    #endregion
+
+    /// <summary>
+    /// 璋冨害鍒嗘瀽杈呭姪绫�
+    /// </summary>
+    public class SchedulingHelper
+    {
+        double _frequency_def = 50;
+        double _frequency_min = 25;
+        double _frequency_max = 50;
+        double _frequency_space = 0.1;//棰戠巼闂撮殧  
+
+        double _head_space = 0.1;//鎵▼闂撮殧
+
+        #region RunFlag
+        string _falgFrePumpTag = "B";
+        string _falgFixPumpTag = "G";
+        string _falgSpaceMark = "_";
+
+
+        string GetRunFlag(int[] flags)
+        {
+            var runFlag = string.Empty;
+            var index = 0;
+            var count = flags.Length;
+            foreach (var flag in flags)
+            {
+                runFlag += GetGFlag(flag);
+                index++;
+                if (index != count)
+                {
+                    runFlag += _falgSpaceMark;
+                }
+            }
+            return runFlag;
+        }
+
+        string GetRunFlag(List<int> flags)
+        {
+            var runFlag = string.Empty;
+            var index = 0;
+            var count = flags.Count;
+            foreach (var flag in flags)
+            {
+                runFlag += GetGFlag(flag);
+                index++;
+                if (index != count)
+                {
+                    runFlag += _falgSpaceMark;
+                }
+            }
+            return runFlag;
+        }
+
+        string GetGFlag(int flag)
+        {
+            return _falgFrePumpTag + flag;
+        }
+
+        #endregion
+
+        DAL.ScheduleCombine _dal = new DAL.ScheduleCombine();
+        DAL.ScheduleConclusion _dalScheduleConclusion = new DAL.ScheduleConclusion();
+        DAL.ScheduleAnaLog _dalAnaLog = new DAL.ScheduleAnaLog();
+
+
+        private List<int> _combineFlags1 = new List<int>() { 11, 12, 13, 14, 16, 17, 18 };
+        private List<int> _combineFlags2 = new List<int>() { 15 };
+
+        public void Ana(List<Pump> pumps, double tagetFlow, double tagetHead, List<int> openPumpCombine)
+        {
+            List<int> open_combine_flags_1 = new List<int>();
+            List<int> open_combine_flags_2 = new List<int>();
+
+            if (openPumpCombine != null && openPumpCombine.Any())
+            {
+                foreach (var pump in openPumpCombine)
+                {
+                    if (_combineFlags1.Contains(pump))
+                    {
+                        open_combine_flags_1.Add(pump);
+                    }
+                    else
+                    {
+                        open_combine_flags_2.Add(pump);
+                    }
+                }
+            }
+            else
+            {
+                open_combine_flags_1 = _combineFlags1.ToList();
+                open_combine_flags_2 = _combineFlags2.ToList();
+            }
+
+            List<Combine> combineList1 = null;
+            List<Combine> combineList2 = null;
+
+            var open_combine_flags_1_count = open_combine_flags_1.Count;
+            if (open_combine_flags_1_count > 0)
+            {
+                bool isSingular = false;
+                var combine_flags_combination_list = PermutationAndCombination<int>.GetCombination(open_combine_flags_1.ToArray(), 2);
+                if ((open_combine_flags_1_count % 2) > 0)
+                {
+                    isSingular = true;
+                    foreach (var flag in open_combine_flags_1)
+                    {
+                        combine_flags_combination_list.Add(new int[] { flag });
+                    }
+                }
+
+                var combine_conclusion_dic = new Dictionary<string, List<Entity.ScheduleConclusion>>();
+                foreach (var combine_flags in combine_flags_combination_list)
+                {
+                    var runFlag = GetRunFlag(combine_flags);
+                    if (combine_conclusion_dic.ContainsKey(runFlag))
+                        continue;
+                    var conclusionList = _dalScheduleConclusion.GetList(runFlag, tagetHead);
+                    combine_conclusion_dic[runFlag] = conclusionList;
+                }
+
+                if (combine_conclusion_dic.Count < 1)
+                {
+                    ////鏃犳硶璁$畻
+                    //return;
+                }
+
+                var combine_flags_permutation_list = PermutationAndCombination<int>.GetPermutation(open_combine_flags_1.ToArray());
+                foreach (var combine_flags_permutation in combine_flags_permutation_list)
+                {
+                    var combine_part_flags_list = new List<int[]>();
+                    for (int i = 0; i < combine_flags_permutation.Length / 2; i++)
+                    {
+                        var flags = combine_flags_permutation.Skip(i * 2).Take(2).ToArray();
+                        combine_part_flags_list.Add(flags);
+                    }
+                    if (isSingular)
+                    {
+                        var last_flag = combine_flags_permutation[combine_flags_permutation.Length - 1];
+                        combine_part_flags_list.Add(new int[] { last_flag });
+                    }
+                    if (combine_part_flags_list.Count < 1)
+                        continue;
+
+
+                    List<Combine> combines = new List<Combine>();
+                    foreach (var combine_part_flags in combine_part_flags_list)
+                    {
+                        var runFlag = GetRunFlag(combine_part_flags);
+
+                    }
+
+
+                }
+
+
+            }
+
+        }
+
+
+
+
+        private OptimalCombine AnaOptimalCombine(List<Combine> combineList1, List<Combine> combineList2, double targetFlow, double targetHead)
+        {
+            double flowDeviation = targetFlow;
+            double totalPower = double.MaxValue;
+            double totalFlow = double.MaxValue;
+
+            Combine optimalCombine1 = null;
+            Combine optimalCombine2 = null;
+            for (int combineIndex1 = 0; combineIndex1 < combineList1.Count; combineIndex1++)
+            {
+                for (int combineIndex2 = 0; combineIndex2 < combineList2.Count; combineIndex2++)
+                {
+                    var combine1 = combineList1[combineIndex1];
+                    var combine2 = combineList2[combineIndex2];
+
+                    var combineTotalFlow = combine1.Flow + combine2.Flow;
+                    var combineTotalPower = combine1.Power + combine2.Power;
+
+                    var diffFlow = Math.Abs(combineTotalFlow - targetFlow);
+                    if (diffFlow < flowDeviation)
+                    {
+                        optimalCombine1 = combine1;
+                        optimalCombine2 = combine2;
+                        totalPower = combine1.Power + combine2.Power;
+                        totalFlow = combineTotalFlow;
+                        flowDeviation = diffFlow;
+                    }
+
+                    if (diffFlow < targetFlow * 0.01 && combineTotalPower < totalPower)
+                    {
+                        optimalCombine1 = combine1;
+                        optimalCombine2 = combine2;
+                        totalPower = combine1.Power + combine2.Power;
+                        totalFlow = combineTotalFlow;
+                    }
+
+                }
+            }
+            if (optimalCombine1 == null && optimalCombine2 == null)
+                return default;
+            var optimalCombine = new OptimalCombine();
+            optimalCombine.Combines = new List<Combine>();
+            if (optimalCombine1 != null)
+            {
+                optimalCombine.Combines.Add(optimalCombine1);
+            }
+            if (optimalCombine2 != null)
+            {
+                optimalCombine.Combines.Add(optimalCombine2);
+            }
+            optimalCombine.Flow = totalFlow;
+            optimalCombine.Power = totalPower;
+            return optimalCombine;
+        }
+
+        /// <summary>
+        /// 鎻掑叆鍒嗘瀽鏃ュ織
+        /// </summary> 
+        private void InsertAnaLog(string info)
+        {
+            var entity = new Entity.ScheduleAnaLog(info);
+            _dalAnaLog.Insert(entity);
+        }
+
+
+        /// <summary>
+        /// 鍒ゆ柇琛ㄦ槸鍚﹀瓨鍦�
+        /// </summary>
+        public bool ExistTable(string runFlag)
+        {
+            return _dal.ExistTable(runFlag);
+        }
+
+    }
+}
diff --git "a/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0504\051.cs" "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0504\051.cs"
new file mode 100644
index 0000000..f3d2535
--- /dev/null
+++ "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0504\051.cs"
@@ -0,0 +1,291 @@
+锘縰sing IStation.Model;
+
+namespace IStation.Algorithm
+{
+
+    #region ViewModel
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class Combine
+    {
+        public Combine() { }
+        public List<int> PumpIds { get; set; }
+        public string RunFlag { get; set; }
+        public int RunCount { get; set; }
+        public double Frequency { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+        public double Power { get; set; }
+    }
+
+
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class OptimalCombine
+    {
+        public OptimalCombine() { }
+        public List<int> PumpIds { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+        public double Power { get; set; }
+        public List<Combine> Combines { get; set; }
+    }
+
+    #endregion
+
+    /// <summary>
+    /// 璋冨害鍒嗘瀽杈呭姪绫�
+    /// </summary>
+    public class SchedulingHelper
+    {
+        double _frequency_def = 50;
+        double _frequency_min = 25;
+        double _frequency_max = 50;
+        double _frequency_space = 0.1;//棰戠巼闂撮殧  
+
+        double _head_space = 0.1;//鎵▼闂撮殧
+
+        #region RunFlag
+        string _falgFrePumpTag = "B";
+        string _falgFixPumpTag = "G";
+        string _falgSpaceMark = "_";
+
+
+        string GetRunFlag(int[] flags)
+        {
+            var runFlag = string.Empty;
+            var index = 0;
+            var count = flags.Length;
+            foreach (var flag in flags)
+            {
+                runFlag += GetGFlag(flag);
+                index++;
+                if (index != count)
+                {
+                    runFlag += _falgSpaceMark;
+                }
+            }
+            return runFlag;
+        }
+
+        string GetRunFlag(List<int> flags)
+        {
+            var runFlag = string.Empty;
+            var index = 0;
+            var count = flags.Count;
+            foreach (var flag in flags)
+            {
+                runFlag += GetGFlag(flag);
+                index++;
+                if (index != count)
+                {
+                    runFlag += _falgSpaceMark;
+                }
+            }
+            return runFlag;
+        }
+
+        string GetGFlag(int flag)
+        {
+            return _falgFrePumpTag + flag;
+        }
+
+        #endregion
+
+        DAL.ScheduleCombine _dal = new DAL.ScheduleCombine();
+        DAL.ScheduleConclusion _dalScheduleConclusion = new DAL.ScheduleConclusion();
+        DAL.ScheduleAnaLog _dalAnaLog = new DAL.ScheduleAnaLog();
+
+
+        private List<int> _combineFlags1 = new List<int>() { 11, 12, 13, 14, 16, 17, 18 };
+        private List<int> _combineFlags2 = new List<int>() { 15 };
+
+        public void Ana(List<Pump> pumps, double tagetFlow, double tagetHead, List<int> openPumpCombine)
+        {
+            List<int> open_combine_flags_1 = new List<int>();
+            List<int> open_combine_flags_2 = new List<int>();
+
+            if (openPumpCombine != null && openPumpCombine.Any())
+            {
+                foreach (var pump in openPumpCombine)
+                {
+                    if (_combineFlags1.Contains(pump))
+                    {
+                        open_combine_flags_1.Add(pump);
+                    }
+                    else
+                    {
+                        open_combine_flags_2.Add(pump);
+                    }
+                }
+            }
+            else
+            {
+                open_combine_flags_1 = _combineFlags1.ToList();
+                open_combine_flags_2 = _combineFlags2.ToList();
+            }
+
+            List<Combine> combineList1 = null;
+            List<Combine> combineList2 = null;
+
+            var open_combine_flags_1_count = open_combine_flags_1.Count;
+            if (open_combine_flags_1_count > 0)
+            {
+                bool isSingular = false;
+                var combine_flags_combination_list = PermutationAndCombination<int>.GetCombination(open_combine_flags_1.ToArray(), 2);
+                if ((open_combine_flags_1_count % 2) > 0)
+                {
+                    isSingular = true;
+                    foreach (var flag in open_combine_flags_1)
+                    {
+                        combine_flags_combination_list.Add(new int[] { flag });
+                    }
+                }
+
+                var combine_conclusion_dic = new Dictionary<string, List<Entity.ScheduleConclusion>>();
+                foreach (var combine_flags in combine_flags_combination_list)
+                {
+                    var runFlag = GetRunFlag(combine_flags);
+                    if (combine_conclusion_dic.ContainsKey(runFlag))
+                        continue;
+                    var conclusionList = _dalScheduleConclusion.GetList(runFlag, tagetHead);
+                    combine_conclusion_dic[runFlag] = conclusionList;
+                }
+
+                if (combine_conclusion_dic.Count < 1)
+                {
+                    ////鏃犳硶璁$畻
+                    //return;
+                }
+
+                var combine_flags_permutation_list = PermutationAndCombination<int>.GetPermutation(open_combine_flags_1.ToArray());
+                for (int i = 0; i < length; i++)
+                {
+
+                }
+                foreach (var combine_flags_permutation in combine_flags_permutation_list)
+                {
+                    var combine_part_flags_list = new List<int[]>();
+                    for (int i = 0; i < combine_flags_permutation.Length / 2; i++)
+                    {
+                        var flags = combine_flags_permutation.Skip(i * 2).Take(2).ToArray();
+                        combine_part_flags_list.Add(flags);
+                    }
+                    if (isSingular)
+                    {
+                        var last_flag = combine_flags_permutation[combine_flags_permutation.Length - 1];
+                        combine_part_flags_list.Add(new int[] { last_flag });
+                    }
+                    if (combine_part_flags_list.Count < 1)
+                        continue;
+
+
+                    List<Combine> combines = new List<Combine>();
+                    Dictionary<double, List<Combine>> combines_fre_list = new Dictionary<double, List<Combine>>();
+
+                    for (double fre = _frequency_max; fre >= _frequency_min; fre -= _frequency_space)
+                    {
+                        var freItem = new AnaPumpFreItem();
+                        freItem.Frequency = Math.Round(fre, 1);
+                        freItem.CurveQH = Curve.PumpCalculateHelper.CalculateSimilarQH(this.CurveQH, freDef, fre);
+                        freItem.CurveQP = Curve.PumpCalculateHelper.CalculateSimilarQP(this.CurveQP, freDef, fre);
+                        this.AnaFrequencyItems.Add(freItem);
+                    }
+
+                    foreach (var combine_part_flags in combine_part_flags_list)
+                    {
+                        var runFlag = GetRunFlag(combine_part_flags);
+
+
+                    }
+
+
+                }
+
+
+            }
+
+        }
+
+
+
+
+        private OptimalCombine AnaOptimalCombine(List<Combine> combineList1, List<Combine> combineList2, double targetFlow, double targetHead)
+        {
+            double flowDeviation = targetFlow;
+            double totalPower = double.MaxValue;
+            double totalFlow = double.MaxValue;
+
+            Combine optimalCombine1 = null;
+            Combine optimalCombine2 = null;
+            for (int combineIndex1 = 0; combineIndex1 < combineList1.Count; combineIndex1++)
+            {
+                for (int combineIndex2 = 0; combineIndex2 < combineList2.Count; combineIndex2++)
+                {
+                    var combine1 = combineList1[combineIndex1];
+                    var combine2 = combineList2[combineIndex2];
+
+                    var combineTotalFlow = combine1.Flow + combine2.Flow;
+                    var combineTotalPower = combine1.Power + combine2.Power;
+
+                    var diffFlow = Math.Abs(combineTotalFlow - targetFlow);
+                    if (diffFlow < flowDeviation)
+                    {
+                        optimalCombine1 = combine1;
+                        optimalCombine2 = combine2;
+                        totalPower = combine1.Power + combine2.Power;
+                        totalFlow = combineTotalFlow;
+                        flowDeviation = diffFlow;
+                    }
+
+                    if (diffFlow < targetFlow * 0.01 && combineTotalPower < totalPower)
+                    {
+                        optimalCombine1 = combine1;
+                        optimalCombine2 = combine2;
+                        totalPower = combine1.Power + combine2.Power;
+                        totalFlow = combineTotalFlow;
+                    }
+
+                }
+            }
+            if (optimalCombine1 == null && optimalCombine2 == null)
+                return default;
+            var optimalCombine = new OptimalCombine();
+            optimalCombine.Combines = new List<Combine>();
+            if (optimalCombine1 != null)
+            {
+                optimalCombine.Combines.Add(optimalCombine1);
+            }
+            if (optimalCombine2 != null)
+            {
+                optimalCombine.Combines.Add(optimalCombine2);
+            }
+            optimalCombine.Flow = totalFlow;
+            optimalCombine.Power = totalPower;
+            return optimalCombine;
+        }
+
+        /// <summary>
+        /// 鎻掑叆鍒嗘瀽鏃ュ織
+        /// </summary> 
+        private void InsertAnaLog(string info)
+        {
+            var entity = new Entity.ScheduleAnaLog(info);
+            _dalAnaLog.Insert(entity);
+        }
+
+
+        /// <summary>
+        /// 鍒ゆ柇琛ㄦ槸鍚﹀瓨鍦�
+        /// </summary>
+        public bool ExistTable(string runFlag)
+        {
+            return _dal.ExistTable(runFlag);
+        }
+
+    }
+}
diff --git "a/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0505\051.cs" "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0505\051.cs"
new file mode 100644
index 0000000..258f7a3
--- /dev/null
+++ "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266\0505\051.cs"
@@ -0,0 +1,290 @@
+锘縩amespace IStation.Algorithm
+{
+
+    #region ViewModel
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class Combine
+    {
+        public Combine() { }
+        public List<int> PumpIds { get; set; }
+        public string RunFlag { get; set; }
+        public int RunCount { get; set; }
+        public double Frequency { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+        public double Power { get; set; }
+    }
+
+
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class OptimalCombine
+    {
+        public OptimalCombine() { }
+        public List<int> PumpIds { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+        public double Power { get; set; }
+        public List<Combine> Combines { get; set; }
+    }
+
+    #endregion
+
+    /// <summary>
+    /// 璋冨害鍒嗘瀽杈呭姪绫�
+    /// </summary>
+    public class SchedulingHelper
+    {
+        double _frequency_def = 50;
+        double _frequency_min = 25;
+        double _frequency_max = 50;
+        double _frequency_space = 0.1;//棰戠巼闂撮殧  
+
+        double _head_space = 0.1;//鎵▼闂撮殧
+
+        #region RunFlag
+        string _falgFrePumpTag = "B";
+        string _falgFixPumpTag = "G";
+        string _falgSpaceMark = "_";
+
+
+        string GetRunFlag(int[] flags)
+        {
+            var runFlag = string.Empty;
+            var index = 0;
+            var count = flags.Length;
+            foreach (var flag in flags)
+            {
+                runFlag += GetGFlag(flag);
+                index++;
+                if (index != count)
+                {
+                    runFlag += _falgSpaceMark;
+                }
+            }
+            return runFlag;
+        }
+
+        string GetRunFlag(List<int> flags)
+        {
+            var runFlag = string.Empty;
+            var index = 0;
+            var count = flags.Count;
+            foreach (var flag in flags)
+            {
+                runFlag += GetGFlag(flag);
+                index++;
+                if (index != count)
+                {
+                    runFlag += _falgSpaceMark;
+                }
+            }
+            return runFlag;
+        }
+
+        string GetGFlag(int flag)
+        {
+            return _falgFrePumpTag + flag;
+        }
+
+        #endregion
+
+        DAL.ScheduleCombine _dal = new DAL.ScheduleCombine();
+        DAL.ScheduleConclusion _dalScheduleConclusion = new DAL.ScheduleConclusion();
+        DAL.ScheduleAnaLog _dalAnaLog = new DAL.ScheduleAnaLog();
+
+
+        private List<int> _combineFlags1 = new List<int>() { 11, 12, 13, 14, 16, 17, 18 };
+        private List<int> _combineFlags2 = new List<int>() { 15 };
+
+        public void Ana(List<Pump> pumps, double tagetFlow, double tagetHead)
+        {
+            List<int> open_combine_flags_1 = new List<int>();
+            List<int> open_combine_flags_2 = new List<int>();
+
+
+            if (openPumpCombine != null && openPumpCombine.Any())
+            {
+                foreach (var pump in openPumpCombine)
+                {
+                    if (_combineFlags1.Contains(pump))
+                    {
+                        open_combine_flags_1.Add(pump);
+                    }
+                    else
+                    {
+                        open_combine_flags_2.Add(pump);
+                    }
+                }
+            }
+            else
+            {
+                open_combine_flags_1 = _combineFlags1.ToList();
+                open_combine_flags_2 = _combineFlags2.ToList();
+            }
+
+            List<Combine> combineList1 = null;
+            List<Combine> combineList2 = null;
+
+            var open_combine_flags_1_count = open_combine_flags_1.Count;
+            if (open_combine_flags_1_count > 0)
+            {
+                bool isSingular = false;
+                var combine_flags_combination_list = PermutationAndCombination<int>.GetCombination(open_combine_flags_1.ToArray(), 2);
+                if ((open_combine_flags_1_count % 2) > 0)
+                {
+                    isSingular = true;
+                    foreach (var flag in open_combine_flags_1)
+                    {
+                        combine_flags_combination_list.Add(new int[] { flag });
+                    }
+                }
+
+                var combine_conclusion_dic = new Dictionary<string, List<Entity.ScheduleConclusion>>();
+                foreach (var combine_flags in combine_flags_combination_list)
+                {
+                    var runFlag = GetRunFlag(combine_flags);
+                    if (combine_conclusion_dic.ContainsKey(runFlag))
+                        continue;
+                    var conclusionList = _dalScheduleConclusion.GetList(runFlag, tagetHead);
+                    combine_conclusion_dic[runFlag] = conclusionList;
+                }
+
+                if (combine_conclusion_dic.Count < 1)
+                {
+                    ////鏃犳硶璁$畻
+                    //return;
+                }
+
+                var combine_flags_permutation_list = PermutationAndCombination<int>.GetPermutation(open_combine_flags_1.ToArray());
+                for (int i = 0; i < length; i++)
+                {
+
+                }
+                foreach (var combine_flags_permutation in combine_flags_permutation_list)
+                {
+                    var combine_part_flags_list = new List<int[]>();
+                    for (int i = 0; i < combine_flags_permutation.Length / 2; i++)
+                    {
+                        var flags = combine_flags_permutation.Skip(i * 2).Take(2).ToArray();
+                        combine_part_flags_list.Add(flags);
+                    }
+                    if (isSingular)
+                    {
+                        var last_flag = combine_flags_permutation[combine_flags_permutation.Length - 1];
+                        combine_part_flags_list.Add(new int[] { last_flag });
+                    }
+                    if (combine_part_flags_list.Count < 1)
+                        continue;
+
+
+                    List<Combine> combines = new List<Combine>();
+                    Dictionary<double, List<Combine>> combines_fre_list = new Dictionary<double, List<Combine>>();
+
+                    for (double fre = _frequency_max; fre >= _frequency_min; fre -= _frequency_space)
+                    {
+                        var freItem = new AnaPumpFreItem();
+                        freItem.Frequency = Math.Round(fre, 1);
+                        freItem.CurveQH = Curve.PumpCalculateHelper.CalculateSimilarQH(this.CurveQH, freDef, fre);
+                        freItem.CurveQP = Curve.PumpCalculateHelper.CalculateSimilarQP(this.CurveQP, freDef, fre);
+                        this.AnaFrequencyItems.Add(freItem);
+                    }
+
+                    foreach (var combine_part_flags in combine_part_flags_list)
+                    {
+                        var runFlag = GetRunFlag(combine_part_flags);
+
+
+                    }
+
+
+                }
+
+
+            }
+
+        }
+
+
+
+
+        private OptimalCombine AnaOptimalCombine(List<Combine> combineList1, List<Combine> combineList2, double targetFlow, double targetHead)
+        {
+            double flowDeviation = targetFlow;
+            double totalPower = double.MaxValue;
+            double totalFlow = double.MaxValue;
+
+            Combine optimalCombine1 = null;
+            Combine optimalCombine2 = null;
+            for (int combineIndex1 = 0; combineIndex1 < combineList1.Count; combineIndex1++)
+            {
+                for (int combineIndex2 = 0; combineIndex2 < combineList2.Count; combineIndex2++)
+                {
+                    var combine1 = combineList1[combineIndex1];
+                    var combine2 = combineList2[combineIndex2];
+
+                    var combineTotalFlow = combine1.Flow + combine2.Flow;
+                    var combineTotalPower = combine1.Power + combine2.Power;
+
+                    var diffFlow = Math.Abs(combineTotalFlow - targetFlow);
+                    if (diffFlow < flowDeviation)
+                    {
+                        optimalCombine1 = combine1;
+                        optimalCombine2 = combine2;
+                        totalPower = combine1.Power + combine2.Power;
+                        totalFlow = combineTotalFlow;
+                        flowDeviation = diffFlow;
+                    }
+
+                    if (diffFlow < targetFlow * 0.01 && combineTotalPower < totalPower)
+                    {
+                        optimalCombine1 = combine1;
+                        optimalCombine2 = combine2;
+                        totalPower = combine1.Power + combine2.Power;
+                        totalFlow = combineTotalFlow;
+                    }
+
+                }
+            }
+            if (optimalCombine1 == null && optimalCombine2 == null)
+                return default;
+            var optimalCombine = new OptimalCombine();
+            optimalCombine.Combines = new List<Combine>();
+            if (optimalCombine1 != null)
+            {
+                optimalCombine.Combines.Add(optimalCombine1);
+            }
+            if (optimalCombine2 != null)
+            {
+                optimalCombine.Combines.Add(optimalCombine2);
+            }
+            optimalCombine.Flow = totalFlow;
+            optimalCombine.Power = totalPower;
+            return optimalCombine;
+        }
+
+        /// <summary>
+        /// 鎻掑叆鍒嗘瀽鏃ュ織
+        /// </summary> 
+        private void InsertAnaLog(string info)
+        {
+            var entity = new Entity.ScheduleAnaLog(info);
+            _dalAnaLog.Insert(entity);
+        }
+
+
+        /// <summary>
+        /// 鍒ゆ柇琛ㄦ槸鍚﹀瓨鍦�
+        /// </summary>
+        public bool ExistTable(string runFlag)
+        {
+            return _dal.ExistTable(runFlag);
+        }
+
+    }
+}
diff --git "a/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266.cs" "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266.cs"
new file mode 100644
index 0000000..99a5518
--- /dev/null
+++ "b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper - \345\244\215\345\210\266.cs"
@@ -0,0 +1,255 @@
+锘縰sing System;
+
+namespace IStation.Algorithm
+{
+
+    #region ViewModel
+
+    /// <summary>
+    /// 鍒嗘瀽娉甸」
+    /// </summary>
+    public class AnaItem
+    {
+        public AnaItem() { }
+        public string RunFlag { get; set; }
+        public int RunCount { get; set; }
+        public List<long> PumpIds { get; set; }
+        public double Flow { get; set; }
+        public double Head { get; set; }
+    }
+
+    #endregion
+
+    /// <summary>
+    /// 璋冨害鍒嗘瀽杈呭姪绫�
+    /// </summary>
+    public class SchedulingHelper
+    {
+        double _frequency_def = 50;
+        double _frequency_min = 25;
+        double _frequency_max = 50;
+        double _frequency_space = 0.1;//棰戠巼闂撮殧  
+
+        double _head_space = 0.1;//鎵▼闂撮殧
+
+        #region RunFlag
+        string _falgFrePumpTag = "B";
+        string _falgFixPumpTag = "G";
+        string _falgSpaceMark = "_";
+
+        string GetRunFlag(List<AnaPumpItem> pumpItems)
+        {
+            var tableName = string.Empty;
+            var count = pumpItems.Count;
+            pumpItems = pumpItems.OrderBy(p => p.ID).ToList();
+            for (int i = 0; i < count; i++)
+            {
+                var pumpItem = pumpItems[i];
+                tableName += GetRunFlag(pumpItem);
+                if ((i + 1) != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+        string GetRunFlag(AnaPumpItem pumpItem)
+        {
+            return (pumpItem.IsBp ? _falgFrePumpTag : _falgFixPumpTag) + pumpItem.ID;
+        }
+
+
+        string GetRunFlag(Dictionary<int, bool> dic)
+        {
+            var tableName = string.Empty;
+            var index = 0;
+            var count = dic.Count;
+            foreach (var item in dic)
+            {
+                tableName += GetRunFlag(item.Key, item.Value);
+                index++;
+                if (index != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+        string GetRunFlag(long id, bool isBp)
+        {
+            return (isBp ? _falgFrePumpTag : _falgFixPumpTag) + id;
+        }
+
+        string GetRunFlag(List<string> flags)
+        {
+            var tableName = string.Empty;
+            var count = flags.Count;
+            var index = 0;
+            foreach (var flag in flags)
+            {
+                tableName += flag;
+                index++;
+                if (index != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+        string GetRunFlag(List<int> flags)
+        {
+            var tableName = string.Empty;
+            var count = flags.Count;
+            var index = 0;
+            foreach (var flag in flags)
+            {
+                tableName += flag;
+                index++;
+                if (index != count)
+                {
+                    tableName += _falgSpaceMark;
+                }
+            }
+            return tableName;
+        }
+
+
+        #endregion
+
+        DAL.ScheduleCombine _dal = new DAL.ScheduleCombine();
+        DAL.ScheduleConclusion _dalScheduleConclusion = new DAL.ScheduleConclusion();
+        DAL.ScheduleAnaLog _dalAnaLog = new DAL.ScheduleAnaLog();
+
+
+        public class CurrentViewModel : Entity.ScheduleConclusion
+        {
+            public CurrentViewModel(Entity.ScheduleConclusion rhs) : base(rhs)
+            {
+                this.Flags = new List<int>();
+                var flags = rhs.RunFlag.Split('_');
+                foreach (var item in flags)
+                {
+                    if (int.TryParse(item.Substring(1), out int flag))
+                    {
+                        this.Flags.Add(flag);
+                    }
+
+                }
+            }
+            public List<int> Flags { get; set; }
+        }
+
+
+        public void Ana(List<Pump> pumps, double tagetFlow, double tagetHead, List<int> openPumpCombine)
+        {
+            var pumpIds = pumps.Select(x => x.ID);
+            var dic_pump = pumps.ToDictionary(x => x.ID, x => x.IsBp);
+
+
+
+
+            if (openPumpCombine != null && openPumpCombine.Any())
+            {
+
+                var allCombineList = PermutationAndCombination<int>.GetCombination(pumpIds.ToArray(), 1);
+
+
+
+
+                allCombineList = PermutationAndCombination<int>.GetCombination(pumpIds.ToArray(), 2);
+                var combineList = new List<List<int>>();
+                foreach (var combine in allCombineList)
+                {
+                    var pump1 = combine[0];
+                    var pump2 = combine[1];
+                    if (!openPumpCombine.Contains(pump1))
+                        continue;
+                    if (!openPumpCombine.Contains(pump2))
+                        continue;
+                    combineList.Add(combine.ToList());
+                }
+                if (combineList.Count < 1)
+                    return;
+
+                var avgFlow = tagetFlow / 2;
+
+                var optimalConclusionList = new List<CurrentViewModel>();
+                foreach (var combine in combineList)
+                {
+                    var dic = new Dictionary<int, bool>();
+                    foreach (var pump in combine)
+                    {
+                        if (dic_pump.ContainsKey(pump))
+                        {
+                            dic.Add(pump, dic_pump[pump]);
+                        }
+                    }
+                    var runFalg = GetRunFlag(dic);
+                    var list = _dalScheduleConclusion.GetList(runFalg, avgFlow, tagetHead, 5);
+                    if (list != null && list.Any())
+                    {
+                        var vmList = list.Select(x => new CurrentViewModel(x)).ToList();
+                        optimalConclusionList.AddRange(vmList);
+                    }
+                }
+                if (optimalConclusionList == null || !optimalConclusionList.Any())
+                {
+                    return;
+                }
+
+                var optimalConclusionCombineList = PermutationAndCombination<CurrentViewModel>.GetCombination(optimalConclusionList.ToArray(), 2);
+                var combines = new List<Combine>();
+                foreach (var arr in optimalConclusionCombineList)
+                {
+                    var falgs = arr.SelectMany(x => x.Flags).ToList();
+                    if (falgs.GroupBy(x => x).Where(x => x.Count() > 1).Count() > 0)
+                    {
+                        continue;
+                    }
+                    var combine = new Combine();
+                    combine.RunFlag = GetRunFlag(falgs);
+                    combine.Power = arr.Sum(x => x.Power);
+                    combine.Head = arr.Average(x => x.Head);
+                    combine.Flow = arr.Sum(x => x.Flow);
+                    combine.RunFlagList = falgs;
+                    combines.Add(combine);
+                }
+
+                var a = combines.OrderBy(x => x.Flow).ThenBy(x => x.Power).ToList();
+            }
+        }
+
+        private class Combine
+        {
+            public double Flow { get; set; }
+            public double Head { get; set; }
+            public double Power { get; set; }
+            public string RunFlag { get; set; }
+            public List<int> RunFlagList { get; set; }
+        }
+
+
+
+        /// <summary>
+        /// 鎻掑叆鍒嗘瀽鏃ュ織
+        /// </summary> 
+        private void InsertAnaLog(string info)
+        {
+            var entity = new Entity.ScheduleAnaLog(info);
+            _dalAnaLog.Insert(entity);
+        }
+
+
+        /// <summary>
+        /// 鍒ゆ柇琛ㄦ槸鍚﹀瓨鍦�
+        /// </summary>
+        public bool ExistTable(string runFlag)
+        {
+            return _dal.ExistTable(runFlag);
+        }
+
+    }
+}
diff --git a/Schedule/IStation.Algorithm/Schedule/SchedulingHelper.cs b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper.cs
index 9f08205..0e9e97c 100644
--- a/Schedule/IStation.Algorithm/Schedule/SchedulingHelper.cs
+++ b/Schedule/IStation.Algorithm/Schedule/SchedulingHelper.cs
@@ -1,21 +1,34 @@
-锘縰sing System;
-
-namespace IStation.Algorithm
+锘縩amespace IStation.Algorithm
 {
 
     #region ViewModel
 
     /// <summary>
+    /// 
+    /// </summary>
+    public class FreCombine
+    {
+        public FreCombine() { }
+        public List<int> Flags { get; set; }
+        public int RunCount { get; set; }
+        public double Frequency { get; set; }
+        public double Flow { get; set; }
+        public double Power { get; set; }
+    }
+
+
+
+    /// <summary>
     /// 鍒嗘瀽娉甸」
     /// </summary>
-    public class AnaItem
+    public class OptimalCombine
     {
-        public AnaItem() { }
-        public string RunFlag { get; set; }
-        public int RunCount { get; set; }
-        public List<long> PumpIds { get; set; }
+        public OptimalCombine() { }
+        public List<int> Flags { get; set; }
         public double Flow { get; set; }
         public double Head { get; set; }
+        public double Power { get; set; }
+        public List<FreCombine> Combines { get; set; }
     }
 
     #endregion
@@ -26,9 +39,9 @@
     public class SchedulingHelper
     {
         double _frequency_def = 50;
-        double _frequency_min = 25;
-        double _frequency_max = 50;
-        double _frequency_space = 0.1;//棰戠巼闂撮殧  
+        decimal _frequency_min = 25;
+        decimal _frequency_max = 50;
+        decimal _frequency_space = 0.1m;//棰戠巼闂撮殧  
 
         double _head_space = 0.1;//鎵▼闂撮殧
 
@@ -37,69 +50,45 @@
         string _falgFixPumpTag = "G";
         string _falgSpaceMark = "_";
 
-        string GetRunFlag(List<AnaPumpItem> pumpItems)
-        {
-            var tableName = string.Empty;
-            var count = pumpItems.Count;
-            pumpItems = pumpItems.OrderBy(p => p.ID).ToList();
-            for (int i = 0; i < count; i++)
-            {
-                var pumpItem = pumpItems[i];
-                tableName += GetRunFlag(pumpItem);
-                if ((i + 1) != count)
-                {
-                    tableName += _falgSpaceMark;
-                }
-            }
-            return tableName;
-        }
 
-        string GetRunFlag(AnaPumpItem pumpItem)
+        string GetRunFlag(int[] flags)
         {
-            return (pumpItem.IsBp ? _falgFrePumpTag : _falgFixPumpTag) + pumpItem.ID;
-        }
-
-
-        string GetRunFlag(Dictionary<int, bool> dic)
-        {
-            var tableName = string.Empty;
+            var runFlag = string.Empty;
             var index = 0;
-            var count = dic.Count;
-            foreach (var item in dic)
-            {
-                tableName += GetRunFlag(item.Key, item.Value);
-                index++;
-                if (index != count)
-                {
-                    tableName += _falgSpaceMark;
-                }
-            }
-            return tableName;
-        }
-
-        string GetRunFlag(long id, bool isBp)
-        {
-            return (isBp ? _falgFrePumpTag : _falgFixPumpTag) + id;
-        }
-
-        string GetRunFlag(List<string> flags)
-        {
-            var tableName = string.Empty;
-            var count = flags.Count;
-            var index = 0;
+            var count = flags.Length;
             foreach (var flag in flags)
             {
-                tableName += flag;
+                runFlag += GetGFlag(flag);
                 index++;
                 if (index != count)
                 {
-                    tableName += _falgSpaceMark;
+                    runFlag += _falgSpaceMark;
                 }
             }
-            return tableName;
+            return runFlag;
         }
 
+        string GetRunFlag(List<int> flags)
+        {
+            var runFlag = string.Empty;
+            var index = 0;
+            var count = flags.Count;
+            foreach (var flag in flags)
+            {
+                runFlag += GetGFlag(flag);
+                index++;
+                if (index != count)
+                {
+                    runFlag += _falgSpaceMark;
+                }
+            }
+            return runFlag;
+        }
 
+        string GetGFlag(int flag)
+        {
+            return _falgFrePumpTag + flag;
+        }
 
         #endregion
 
@@ -108,102 +97,182 @@
         DAL.ScheduleAnaLog _dalAnaLog = new DAL.ScheduleAnaLog();
 
 
-        public class CurrentViewModel : Entity.ScheduleConclusion
+        private List<int> _combineFlags1 = new List<int>() { 11, 12, 13, 14, 16, 17, 18 };
+        private List<int> _combineFlags2 = new List<int>() { 15 };
+
+        public void Ana(List<Pump> pumps, double taget_flow, double tagetHead)
         {
-            public CurrentViewModel(Entity.ScheduleConclusion rhs) : base(rhs)
+            tagetHead = Math.Round(tagetHead);
+            var pump_flag_list = pumps.Select(x => x.ID).ToList();
+            for (int pumpCount = 1; pumpCount <= pumps.Count; pumpCount++)
             {
-                this.Flags = new List<int>();
-                var flags = rhs.RunFlag.Split('_');
-                foreach (var item in flags)
+                var combine_list = PermutationAndCombination<int>.GetCombination(pump_flag_list.ToArray(), pumpCount);
+                foreach (var combine in combine_list)
                 {
-                    if (int.TryParse(item.Substring(1), out int flag))
-                    {
-                        this.Flags.Add(flag);
-                    }
+                    List<int> combine_flag_list_part1 = new List<int>();
+                    List<int> combine_flag_list_part2 = new List<int>();
 
-                }
-            }
-            public List<int> Flags { get; set; }
-        }
-
-
-        public void Ana(List<Pump> pumps, double tagetFlow, double tagetHead, List<int> openPumpCombine)
-        {
-            var pumpIds = pumps.Select(x => x.ID);
-            var dic_pump = pumps.ToDictionary(x => x.ID, x => x.IsBp);
-            if (openPumpCombine != null && openPumpCombine.Any())
-            {
-                var allCombineList = PermutationAndCombination<int>.GetCombination(pumpIds.ToArray(), 2);
-                var combineList = new List<List<int>>();
-                foreach (var combine in allCombineList)
-                {
-                    var pump1 = combine[0];
-                    var pump2 = combine[1];
-                    if (!openPumpCombine.Contains(pump1))
-                        continue;
-                    if (!openPumpCombine.Contains(pump2))
-                        continue;
-                    combineList.Add(combine.ToList());
-                }
-                if (combineList.Count < 1)
-                    return;
-
-                var avgFlow = tagetFlow / 2;
-
-                var optimalConclusionList = new List<CurrentViewModel>();
-                foreach (var combine in combineList)
-                {
-                    var dic = new Dictionary<int, bool>();
                     foreach (var pump in combine)
                     {
-                        if (dic_pump.ContainsKey(pump))
+                        if (_combineFlags1.Contains(pump))
                         {
-                            dic.Add(pump, dic_pump[pump]);
+                            combine_flag_list_part1.Add(pump);
+                        }
+                        else
+                        {
+                            combine_flag_list_part2.Add(pump);
                         }
                     }
-                    var runFalg = GetRunFlag(dic);
-                    var list = _dalScheduleConclusion.GetList(runFalg, avgFlow, tagetHead, 1);
-                    if (list != null && list.Any())
+
+
+                    List<FreCombine> fre_combine_list_part1 = new List<FreCombine>();
+                    List<FreCombine> fre_combine_list_part2 = new List<FreCombine>();
+
+                    if (combine_flag_list_part1.Count > 0)
                     {
-                        var vmList = list.Select(x => new CurrentViewModel(x)).ToList();
-                        optimalConclusionList.AddRange(vmList);
+                        var conclusion_list_dic = new Dictionary<int, List<Entity.ScheduleConclusion>>();
+                        foreach (var flag in combine_flag_list_part1)
+                        {
+                            var runFlag = GetGFlag(flag);
+                            if (conclusion_list_dic.ContainsKey(flag))
+                                continue;
+                            var conclusionList = _dalScheduleConclusion.GetList(runFlag, tagetHead);
+                            conclusion_list_dic[flag] = conclusionList;
+                        }
+
+                        if (conclusion_list_dic.Count < 1)
+                        {
+                            continue;
+                        }
+
+                        for (decimal fre = _frequency_max; fre >= _frequency_min; fre -= _frequency_space)
+                        {
+                            var freCombine = new FreCombine();
+                            freCombine.Frequency = (double)fre;
+                            freCombine.Flags = new List<int>();
+                            foreach (var item in conclusion_list_dic)
+                            {
+                                var conclusion = item.Value.Find(x => x.Pump1 == (double)fre);
+                                if (conclusion != null)
+                                {
+                                    freCombine.Flags.Add(item.Key);
+                                    freCombine.Flow += conclusion.Flow;
+                                    freCombine.Power += conclusion.Power;
+                                    freCombine.RunCount++;
+                                }
+                            }
+                            if (freCombine.Flags.Count < 1)
+                                continue;
+                            fre_combine_list_part1.Add(freCombine);
+                        }
+
+
+
+
                     }
-                }
-                if (optimalConclusionList == null || !optimalConclusionList.Any())
-                {
-                    return;
+
+                    if (combine_flag_list_part2.Count > 0)
+                    {
+                        var conclusion_list_dic = new Dictionary<int, List<Entity.ScheduleConclusion>>();
+                        foreach (var flag in combine_flag_list_part2)
+                        {
+                            var runFlag = GetGFlag(flag);
+                            if (conclusion_list_dic.ContainsKey(flag))
+                                continue;
+                            var conclusionList = _dalScheduleConclusion.GetList(runFlag, tagetHead);
+                            conclusion_list_dic[flag] = conclusionList;
+                        }
+
+                        if (conclusion_list_dic.Count < 1)
+                        {
+                            continue;
+                        }
+
+                        for (decimal fre = _frequency_max; fre >= _frequency_min; fre -= _frequency_space)
+                        {
+                            var freCombine = new FreCombine();
+                            freCombine.Frequency = (double)fre;
+                            freCombine.Flags = new List<int>();
+                            foreach (var item in conclusion_list_dic)
+                            {
+                                var conclusion = item.Value.Find(x => x.Pump1 == (double)fre);
+                                if (conclusion != null)
+                                {
+                                    freCombine.Flags.Add(item.Key);
+                                    freCombine.Flow += conclusion.Flow;
+                                    freCombine.Power += conclusion.Power;
+                                    freCombine.RunCount++;
+                                }
+                            }
+                            if (freCombine.Flags.Count < 1)
+                                continue;
+                            fre_combine_list_part2.Add(freCombine);
+                        }
+                    }
+
+
+                    var optimalCombine = AnaOptimalCombine(fre_combine_list_part1, fre_combine_list_part2, taget_flow);
                 }
 
-                var optimalConclusionCombineList = PermutationAndCombination<CurrentViewModel>.GetCombination(optimalConclusionList.ToArray(), 2);
-                var combines = new List<Combine>();
-                foreach (var arr in optimalConclusionCombineList)
-                {
-                    var falgs = arr.SelectMany(x => x.Flags).ToList();
-                    if (falgs.GroupBy(x => x).Where(x => x.Count() > 1).Count() > 0)
-                    {
-                        continue;
-                    }
-                    var combine = new Combine();
-                    combine.Power = arr.Sum(x => x.Power);
-                    combine.Head = arr.Average(x => x.Head);
-                    combine.Flow = arr.Sum(x => x.Flow);
-                    combine.RunFlagList = falgs;
-                    combines.Add(combine);
-                }
-
-                var a = combines;
             }
+
         }
 
-        private class Combine
+
+        private OptimalCombine AnaOptimalCombine(List<FreCombine> fre_combine_list_part1, List<FreCombine> fre_combine_list_part2, double target_flow)
         {
-            public double Flow { get; set; }
-            public double Head { get; set; }
-            public double Power { get; set; }
-            public List<int> RunFlagList { get; set; }
+            double flow_deviation = target_flow;
+            double total_power = double.MaxValue;
+            double total_flow = double.MaxValue;
+
+            FreCombine optimal_combine_part1 = null;
+            FreCombine optimal_combine_part2 = null;
+            for (int Index_part1 = 0; Index_part1 < fre_combine_list_part1.Count; Index_part1++)
+            {
+                for (int Index_part2 = 0; Index_part2 < fre_combine_list_part2.Count; Index_part2++)
+                {
+                    var fre_combine1 = fre_combine_list_part1[Index_part1];
+                    var fre_combine2 = fre_combine_list_part2[Index_part2];
+
+                    var current_flow = fre_combine1.Flow + fre_combine2.Flow;
+                    var current_power = fre_combine1.Power + fre_combine2.Power;
+
+                    var diff_flow = Math.Abs(current_flow - target_flow);
+                    if (diff_flow < flow_deviation)
+                    {
+                        optimal_combine_part1 = fre_combine1;
+                        optimal_combine_part2 = fre_combine2;
+                        total_power = fre_combine1.Power + fre_combine2.Power;
+                        total_flow = current_flow;
+                        flow_deviation = diff_flow;
+                    }
+
+                    if (diff_flow < target_flow * 0.01 && current_power < total_power)
+                    {
+                        optimal_combine_part1 = fre_combine1;
+                        optimal_combine_part2 = fre_combine2;
+                        total_power = fre_combine1.Power + fre_combine2.Power;
+                        total_flow = current_flow;
+                    }
+
+                }
+            }
+            if (optimal_combine_part1 == null && optimal_combine_part2 == null)
+                return default;
+            var optimal_combine = new OptimalCombine();
+            optimal_combine.Combines = new List<FreCombine>();
+            if (optimal_combine_part1 != null)
+            {
+                optimal_combine.Combines.Add(optimal_combine_part1);
+            }
+            if (optimal_combine_part2 != null)
+            {
+                optimal_combine.Combines.Add(optimal_combine_part2);
+            }
+            optimal_combine.Flow = total_flow;
+            optimal_combine.Power = total_power;
+            return optimal_combine;
         }
-
-
 
         /// <summary>
         /// 鎻掑叆鍒嗘瀽鏃ュ織
diff --git a/Schedule/IStation.Client/Form1.cs b/Schedule/IStation.Client/Form1.cs
index dbe4601..ddd2388 100644
--- a/Schedule/IStation.Client/Form1.cs
+++ b/Schedule/IStation.Client/Form1.cs
@@ -119,7 +119,7 @@
             var ch1Pumps = JsonHelper.Json2Object<List<Model.Pump>>(ch1_json);
 
             var helper = new Algorithm.SchedulingHelper();
-            helper.Ana(ch1Pumps, targetFlow, targetHead, combineList);
+            helper.Ana(ch1Pumps, targetFlow, targetHead);
         }
     }
 }
\ No newline at end of file

--
Gitblit v1.9.3