Advertisement
Guest User

Untitled

a guest
Apr 23rd, 2019
114
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 10.44 KB | None | 0 0
  1. using System;
  2. using System.Collections.Generic;
  3.  
  4. namespace simplex_method
  5. {
  6. class SimplexMethod
  7. {
  8. List<double> c;
  9. List<double> newc;
  10. List<double> b;
  11. List<double> [] a;
  12. int cnt = 2;// количество иксов
  13. public SimplexMethod( List<double> []aa, List<double> bb, List<double>cc)
  14. {
  15. a = new List<double>[aa.Length];
  16. b = new List<double>();
  17. c = new List<double>();
  18. for (int i = 0; i<aa.Length; i++)
  19. {
  20. a[i] = new List<double>();
  21. for (int j = 0; j<aa[i].Count; j++)
  22. {
  23. a[i].Add(aa[i][j]);
  24. }
  25. b.Add(bb[i]);
  26. }
  27. for (int i = 0; i<cc.Count; i++)
  28. c.Add(cc[i]);
  29. }
  30. public void norm()
  31. {
  32. for (int i = 0; i<b.Count; i++)
  33. {
  34. if (b[i]<0)
  35. {
  36. for (int j = 0; j<b.Count; j++)
  37. if (j == i)
  38. a[j].Add(1);
  39. else
  40. a[j].Add(0);
  41.  
  42. for (int j = 0; j<a[i].Count; j++)
  43. a[i][j]*=-1;
  44. b[i]*=-1;
  45. c.Add(0);
  46. }
  47. }
  48. newc = new List<double>();
  49.  
  50. for (int j = 0; j<c.Count; j++)
  51. newc.Add(0);
  52. for (int j = 0; j<a.Length; j++)
  53. {
  54. newc.Add(-1);
  55. for (int i = 0; i<a.Length; i++)
  56. {
  57. if (i == j)
  58. a[i].Add(1);
  59. else
  60. a[i].Add(0);
  61. }
  62. }
  63.  
  64. }
  65. public List<double> solve()
  66. {
  67. norm(); // после нормализации, целевая функция ищет max sum(-xi), i>3, т.к. 2 икса найти, третий икс гамма
  68.  
  69. List<int> inBazis = new List<int>();
  70. int n = a.Length;
  71. int m = a[0].Count;
  72. for (int i = 0; i<n; i++)
  73. {
  74. inBazis.Add(m - n + i);
  75. }
  76.  
  77.  
  78.  
  79. int step = 0;
  80. while (true)
  81. {
  82. step++;
  83. Console.WriteLine("\nCelevaya function at step " + step);
  84. for (int j = 0; j<m; j++)
  85. Console.Write(newc[j] +" ");
  86. Console.WriteLine();
  87.  
  88. Console.WriteLine("In bazis in the step " + step);
  89. for (int i = 0; i<n; i++)
  90. {
  91. Console.Write(inBazis[i]);
  92. Console.Write(' ');
  93. }
  94.  
  95.  
  96. Console.WriteLine("coefficients in the step " + step);
  97. for (int i = 0; i<n; i++, Console.WriteLine())
  98. {
  99. Console.Write(b[i]+" ");
  100. for (int j = 0; j<m; j++)
  101. Console.Write(a[i][j]+" ");
  102. }
  103.  
  104. List<double> deltas = new List<double>();
  105. List<bool> baddelta = new List<bool>();
  106. for (int j = 0; j<m; j++)
  107. {
  108. double sum = -newc[j];
  109. for (int i = 0; i<n; i++)
  110. sum+=newc[inBazis[i]]*a[i][j];
  111. deltas.Add(sum);
  112. baddelta.Add(false);
  113. }
  114. Console.WriteLine("deltas at the step "+ step);
  115. bool hasnegative = false;
  116. for (int j = 0; j<m; j++)
  117. {
  118. if(deltas[j]<0)
  119. hasnegative = true;
  120. Console.Write(deltas[j]+" ");
  121. }
  122. Console.WriteLine();
  123.  
  124.  
  125. if (!hasnegative) // если отрицательных нет значит план оптимальный
  126. break;
  127. bool ok = true;
  128. int idx = -1;
  129. while (ok)
  130. {
  131. ok = false;
  132. int minidx = -1;
  133. for (int j = 0; j<m; j++)
  134. {
  135. if (deltas[j] < 0 && !baddelta[j])
  136. {
  137. if (minidx == -1)
  138. minidx = j;
  139. else if(deltas[j]<deltas[minidx])
  140. minidx = j;
  141. ok = true;
  142. }
  143. }
  144. bool haspositive = false;
  145. for (int i = 0; i<n; i++)
  146. {
  147. if (a[i][minidx]>0)
  148. {
  149. haspositive = true;
  150. }
  151. }
  152. if (!haspositive)// если в столбце нет положительных значит плохой столбец, смотрим след оценку
  153. baddelta[minidx] = true;
  154. else
  155. {
  156. idx = minidx;
  157. ok = false;
  158. }
  159. }
  160. if (idx == -1)// решения нет
  161. return new List<double>();
  162.  
  163. // нашли ведущий столбец, у которого номер idx, надо апдейтнуть таблицу
  164. // найдем щас че из базиса выкинуть надо и че закинуть
  165. int tokick = -1;
  166. double minsootnoshenie = 0;
  167. for (int i = 0; i<n; i++)
  168. {
  169. if (a[i][idx]>0)
  170. {
  171. double sootn = newc[inBazis[i]]/a[i][idx];
  172. if (tokick == -1)
  173. {
  174. tokick = i;
  175. minsootnoshenie = sootn;
  176. }
  177. else if (sootn < minsootnoshenie)
  178. {
  179. minsootnoshenie = sootn;
  180. tokick = i;
  181. }
  182. }
  183. }
  184. inBazis[tokick] = idx;
  185. double coef = 1.0/a[tokick][idx];
  186. for (int j = 0; j<m; j++)
  187. {
  188. a[tokick][j]*=coef;
  189. }
  190. b[tokick]*=coef;
  191. for (int i = 0; i<n; i++)
  192. {
  193. if (i != tokick)
  194. {
  195. double coef2= a[i][idx];
  196. for (int j = 0; j<m; j++)
  197. {
  198. a[i][j]-=a[tokick][j] * coef2;
  199. }
  200. b[i]-=b[tokick]*coef2;
  201. }
  202. }
  203.  
  204.  
  205. bool canstart2 = true;
  206. for (int i = 0;i<n; i++)
  207. if (inBazis[i]>=m-n+i && b[i]>0)
  208. canstart2 = false;
  209.  
  210. if (canstart2)
  211. {
  212. for (int i = 0; i<n; i++)
  213. {
  214. if(inBazis[i]>=m-n+i)
  215. {
  216. for (int j = 0; j<m-n; j++)
  217. {
  218. if(a[i][j]!=0)
  219. {
  220. double coef3 = 1.0/a[i][j];
  221. inBazis[i] = j;
  222. for (int t = 0; t<m; t++)
  223. a[i][t]*=coef3;
  224. break;
  225. }
  226. }
  227. }
  228. }
  229.  
  230. for (int i = 0; i<newc.Count; i++)
  231. newc[i] = 0;
  232. for (int i = 0; i<c.Count; i++)
  233. newc[i] = c[i];
  234. }
  235. }
  236. List<double> ans = new List<double>();
  237.  
  238. for (int i = 0; i<c.Count; i++)
  239. ans.Add(0);
  240. // подумать про случай когда ans[i]>0 , при i>2!!!
  241. for (int i = 0; i<n; i++)
  242. {
  243. if (inBazis[i]>=c.Count)
  244. return new List<double>();
  245.  
  246. ans[inBazis[i]] = b[i];
  247. }
  248.  
  249.  
  250.  
  251. return ans;
  252. }
  253. }
  254. class Program
  255. {
  256. static void Main(string[] args)
  257. {
  258. List<double> c = new List<double>();
  259. List<double> b = new List<double>();
  260. List<double>[]a = new List<double>[2];
  261. a[0] = new List<double>();
  262. a[1] = new List<double>();
  263. // задача 1
  264. // c.Add(1);
  265. // c.Add(-1);
  266. // c.Add(-1);
  267. // c.Add(-1);
  268. // b.Add(2);
  269. // b.Add(4);
  270. // a[0].Add(1);
  271. // a[0].Add(-1);
  272. // a[0].Add(1);
  273. // a[0].Add(-2);
  274.  
  275. // a[1].Add(1);
  276. // a[1].Add(1);
  277. // a[1].Add(1);
  278. // a[1].Add(1);
  279.  
  280. // задача 2
  281. // c.Add(1);
  282. // c.Add(0);
  283. // c.Add(0);
  284. // c.Add(1);
  285. // b.Add(10);
  286. // b.Add(2);
  287. // a[0].Add(1);
  288. // a[0].Add(1);
  289. // a[0].Add(1);
  290. // a[0].Add(1);
  291. // a[1].Add(2);
  292. // a[1].Add(1);
  293. // a[1].Add(2);
  294. // a[1].Add(1);
  295. c.Add(1);
  296. c.Add(-1);
  297. c.Add(0);
  298. c.Add(0);
  299. b.Add(8);
  300. b.Add(2);
  301. a[0].Add(8);
  302. a[0].Add(4);
  303. a[0].Add(2);
  304. a[0].Add(1);
  305. a[1].Add(2);
  306. a[1].Add(1);
  307. a[1].Add(1);
  308. a[1].Add(2);
  309.  
  310.  
  311.  
  312.  
  313.  
  314. SimplexMethod s = new SimplexMethod(a,b,c);
  315. List<double> ans = s.solve();
  316. Console.WriteLine("x* = ");
  317. for (int i = 0; i<ans.Count; i++)
  318. Console.Write(ans[i]+" ");
  319. }
  320. }
  321. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement