Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- using ElectronicRelayManufacturing.Data.Info;
- using System;
- using System.Collections.Generic;
- using System.Linq;
- using System.Text;
- using System.Threading.Tasks;
- namespace ElectronicRelayManufacturing.Server.Methods
- {
- class SimplexMethod : IMethod
- {
- private decimal[,] _matrix;
- private decimal[] _res;
- private decimal[] _att;
- private string[] _rows;
- private int _xCount = 3;
- private int _restCount;
- public SimplexMethod(FunctionCoefficients funCoefficients, List<Limit> limits)
- {
- _matrix = CreateMatrix(funCoefficients, limits);
- _restCount = limits.Count;
- _rows = CreateRows(funCoefficients, limits);
- _res = CreateRes(funCoefficients, limits);
- _att = new decimal[_res.Length];
- }
- public Result GetResult()
- {
- var stepCount = 0;
- while(IsFine())
- {
- PrintMatrix();
- Step();
- stepCount++;
- }
- var result = new decimal[_xCount];
- for (var i = 0; i < _xCount; i++)
- {
- result[i] = 0;
- }
- for (var i = 0; i < _restCount + 1; i++)
- {
- if (_rows[i][0] == 'x')
- {
- result[int.Parse(_rows[i][1].ToString()) - 1] = _res[i];
- }
- }
- return new Result
- {
- Profit = (double)_res[0],
- RelayCounts = new List<int>
- {
- (int)result[0],
- (int)result[1],
- (int)result[2],
- }
- };
- }
- private void Step()
- {
- var min = 0M;
- var colIndex = -1;
- for (var i = 0; i < _xCount + _restCount; i++)
- {
- if (min > _matrix[0, i])
- {
- min = _matrix[0, i];
- colIndex = i;
- }
- }
- for (var i = 1; i < _restCount + 1; i++)
- {
- if (_matrix[i, colIndex] == 0)
- {
- _att[i] = decimal.MaxValue;
- }
- else
- {
- _att[i] = _res[i] / _matrix[i, colIndex];
- }
- }
- var rowIndex = -1;
- min = decimal.MaxValue;
- for (var i = 1; i < _restCount + 1; i++)
- {
- if (_att[i] > 0 && _att[i] < min)
- {
- min = _att[i];
- rowIndex = i;
- }
- }
- var element = _matrix[rowIndex, colIndex];
- for (var i = 0; i < _xCount + _restCount; i++)
- {
- _matrix[rowIndex, i] = Math.Round(_matrix[rowIndex, i] / element, 2);
- }
- _res[rowIndex] = Math.Round(_res[rowIndex] / element, 2);
- var symbol = colIndex < _xCount ? 'x' : 's';
- var number = colIndex < _xCount ? colIndex + 1 : colIndex - _restCount + 2;
- _rows[rowIndex] = symbol + number.ToString();
- for (var j = 0; j < _restCount + 1; j++)
- {
- if (j != rowIndex)
- {
- var lineForPlus = new decimal[_xCount + _restCount];
- for (var i = 0; i < _xCount + _restCount; i++)
- {
- lineForPlus[i] = Math.Round(_matrix[rowIndex, i] * _matrix[j, colIndex], 2);
- }
- var resForPlus = Math.Round(_res[rowIndex] * _matrix[j, colIndex], 2);
- _res[j] -= resForPlus;
- for (var i = 0; i < _xCount + _restCount; i++)
- {
- _matrix[j, i] -= lineForPlus[i];
- }
- }
- }
- }
- private void PrintMatrix()
- {
- for (int i = 0; i < 1 + _restCount; i++)
- {
- for (int j = 0; j < _xCount + _restCount; j++)
- {
- Console.Write(_matrix[i, j] + " ");
- }
- Console.WriteLine();
- }
- Console.WriteLine();
- }
- private decimal[,] CreateMatrix(FunctionCoefficients funCoefficients, List<Limit> limits)
- {
- var columnCount = 3 + limits.Count;
- var rowCount = 1 + limits.Count;
- var matrix = new decimal[rowCount, columnCount];
- for (int i = 0; i < rowCount; i++)
- for (int j = 0; j < columnCount; j++)
- matrix[i, j] = 0;
- matrix[0, 0] = (decimal)-funCoefficients.X1;
- matrix[0, 1] = (decimal)-funCoefficients.X2;
- matrix[0, 2] = (decimal)-funCoefficients.X3;
- for(int i = 1; i < rowCount; i++)
- {
- for(int j = 0; j < 3; j++)
- {
- matrix[i, j] = (decimal)Math.Abs(limits[i - 1].Coefficients[j]);
- }
- }
- int rowIndexToOne = 0;
- var values = new decimal[]
- {
- 1, 1, -1, -1, -1, -1
- };
- for(int i = 1; i < rowCount; i++)
- {
- for(int j = 3; j < columnCount; j++)
- {
- if(j - 3 == rowIndexToOne)
- {
- matrix[i, j] = values[rowIndexToOne];
- }
- }
- rowIndexToOne += 1;
- }
- return matrix;
- }
- private string[] CreateRows(FunctionCoefficients funCoefficients, List<Limit> limits)
- {
- var rows = new string[_restCount + 1];
- rows[0] = "z";
- for(int i = 1; i < _restCount + 1; i++)
- {
- rows[i] = $"s{i}";
- }
- return rows;
- }
- private decimal[] CreateRes(FunctionCoefficients funCoefficients, List<Limit> limits)
- {
- var res = new decimal[_restCount + 1];
- res[0] = 0;
- int resIndex = 1;
- foreach(var limit in limits)
- {
- res[resIndex++] = (decimal)Math.Abs(limit.Value);
- }
- return res;
- }
- private bool IsFine()
- {
- for (int j = 0; j < _xCount + _restCount; j++)
- {
- if (_matrix[0, j] < 0) return true;
- }
- return false;
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement