SpaceQuester

Untitled

Jun 29th, 2017
373
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 8.30 KB | None | 0 0
  1. #define _USE_MATH_DEFINES
  2. #include "math.h"
  3. #include <stdlib.h>
  4. #include <stdio.h>
  5. #include <locale.h>
  6. #include <time.h>
  7. #include <stdbool.h>
  8.  
  9. #define Neuron_count 20
  10. #define Neuron_count_half Neuron_count / 2
  11.  
  12. #define Equations_per_neuron 4
  13. #define Equations_count Neuron_count * Equations_per_neuron
  14.  
  15. double f[Equations_count];
  16.  
  17. double C_m = 1;
  18.  
  19. double g_K = 36;
  20. double g_Na = 120;
  21. double g_L = 0.3;
  22.  
  23. double E_K = -77;
  24. double E_Na = 55;
  25. double E_L = -54.4;
  26.  
  27. double I_app[Equations_count];
  28.  
  29. const double sigma_G = 0.3;
  30. const double sigma_GN = 0.5;
  31. const double sigma_N = 0.0;
  32.  
  33. double** A;
  34. double** B;
  35. double* C;
  36. double** sigma;
  37.  
  38. double V(int i)
  39. {
  40. return f[i * 4];
  41. }
  42.  
  43. double m(int i)
  44. {
  45. return f[i * 4 + 1];
  46. }
  47.  
  48. double n(int i)
  49. {
  50. return f[i * 4 + 2];
  51. }
  52.  
  53. double h(int i)
  54. {
  55. return f[i * 4 + 3];
  56. }
  57.  
  58. int RandomI(int min, int max)
  59. {
  60. return ((double)rand() / (RAND_MAX - 1)) * (max - min) + min;
  61. }
  62.  
  63. double RandomD(double min, double max)
  64. {
  65. return ((double)rand() / RAND_MAX) * (max - min) + min;
  66. }
  67.  
  68. double alpha_n(double* f, int i)
  69. {
  70. return 0.01 * (V(i) + 55) / (1 - exp(-(V(i) + 55) / 10));
  71. }
  72.  
  73. double beta_n(double* f, int i)
  74. {
  75. return 0.125 * exp(-(V(i) + 65) / 80);
  76. }
  77.  
  78. double alpha_m(double* f, int i)
  79. {
  80. return 0.1 * (V(i) + 40) / (1 - exp(-(V(i) + 40) / 10));
  81. }
  82.  
  83. double beta_m(double* f, int i)
  84. {
  85. return 4 * exp(-(V(i) + 65) / 18);
  86. }
  87.  
  88. double alpha_h(double* f, int i)
  89. {
  90. return 0.07 * exp(-(V(i) + 65) / 20);
  91. }
  92.  
  93. double beta_h(double* f, int i)
  94. {
  95. return 1 / (exp(-(V(i) + 35) / 10) + 1);
  96. }
  97.  
  98. double HodgkinHuxley(int i, double* f)
  99. {
  100. int in = i / 4;
  101. int il = i % 4;
  102.  
  103. switch (il)
  104. {
  105. case 0:
  106. {
  107. //double sum = 0;
  108.  
  109. /*for (int j = 0; j < Neuron_count; j++)
  110. {
  111. sum += sigma[in][j] * A[in][j] * (V(j) - V(in));
  112. }*/
  113.  
  114. /*for (int j = 0; j < C[in]; j++)
  115. {
  116. sum += sigma[in][(int)B[in][j]] * (V((int)B[in][j]) - V(in));
  117. }*/
  118.  
  119. return (g_Na * m(il) * m(il) * m(il) * h(il) * (E_Na - V(il)) + g_K * n(il) * n(il) * n(il) * n(il) * (E_K - V(il)) + g_L * (E_L - V(il)) + I_app[il]) / C_m;
  120. }
  121.  
  122. case 1:
  123. {
  124. return alpha_m(f, il) * (1 - m(il)) - beta_m(f, il) * m(il);
  125. }
  126.  
  127. case 2:
  128. {
  129. return alpha_n(f, il) * (1 - n(il)) - beta_n(f, il) * n(il);
  130. }
  131.  
  132. case 3:
  133. {
  134. return alpha_h(f, il) * (1 - h(il)) - beta_h(f, il) * h(il);
  135. }
  136. }
  137.  
  138. return 0;
  139. }
  140.  
  141. void RungeKutta(double dt, double* f, double* f_next)
  142. {
  143. double k[Equations_count][4];
  144.  
  145. // k1
  146. for (int i = 0; i < Equations_count; i++)
  147. k[i][0] = HodgkinHuxley(i, f) * dt;
  148.  
  149. double phi_k1[Equations_count];
  150. for (int i = 0; i < Equations_count; i++)
  151. phi_k1[i] = f[i] + k[i][0] / 2;
  152.  
  153. // k2
  154. for (int i = 0; i < Equations_count; i++)
  155. k[i][1] = HodgkinHuxley(i, phi_k1) * dt;
  156.  
  157. double phi_k2[Equations_count];
  158. for (int i = 0; i < Equations_count; i++)
  159. phi_k2[i] = f[i] + k[i][1] / 2;
  160.  
  161. // k3
  162. for (int i = 0; i < Equations_count; i++)
  163. k[i][2] = HodgkinHuxley(i, phi_k2) * dt;
  164.  
  165. double phi_k3[Equations_count];
  166. for (int i = 0; i < Equations_count; i++)
  167. phi_k3[i] = f[i] + k[i][2] / 2;
  168.  
  169. // k4
  170. for (int i = 0; i < Equations_count; i++)
  171. k[i][3] = HodgkinHuxley(i, phi_k3) * dt;
  172.  
  173. for (int i = 0; i < Equations_count; i++)
  174. f_next[i] = f[i] + (k[i][0] + 2 * k[i][1] + 2 * k[i][2] + k[i][3]) / 6;
  175. }
  176.  
  177. void CopyArray(double* source, double* target, int N)
  178. {
  179. for (int i = 0; i < N; i++)
  180. target[i] = source[i];
  181. }
  182.  
  183. bool Approximately(double a, double b)
  184. {
  185. if (a < 0)
  186. a = -a;
  187.  
  188. if (b < 0)
  189. b = -b;
  190.  
  191. return a - b <= 0.000001;
  192. }
  193.  
  194. void FillAMatrixZero()
  195. {
  196. for (int i = 0; i < Neuron_count; i++)
  197. {
  198. for (int j = 0; j < Neuron_count; j++)
  199. {
  200. A[i][j] = 0;
  201. }
  202. }
  203. }
  204.  
  205. void FillBCMatrix()
  206. {
  207. for (int i = 0; i < Neuron_count; i++)
  208. {
  209. int bIndex = 0;
  210. C[i] = 0;
  211. for (int j = 0; j < Neuron_count; j++)
  212. {
  213. if (A[i][j] == 1)
  214. {
  215. B[i][bIndex] = j;
  216. bIndex++;
  217. C[i]++;
  218. }
  219. }
  220. }
  221. }
  222.  
  223. void FillSigmaMatrix()
  224. {
  225. for (int i = 0; i < Neuron_count; i++)
  226. {
  227. for (int j = 0; j < Neuron_count; j++)
  228. {
  229. if ((i >= 0 && i < Neuron_count_half) && (j >= 0 || j < Neuron_count_half))
  230. {
  231. sigma[i][j] = sigma_G;
  232. }
  233. if ((((i >= Neuron_count_half && i < Neuron_count) && (j >= 0 && j < Neuron_count_half)) || ((i >= 0 && i < Neuron_count_half) && (j >= Neuron_count_half && j < Neuron_count))))
  234. {
  235. sigma[i][j] = sigma_GN;
  236. }
  237. if ((i >= Neuron_count_half && i < Neuron_count) && (j >= Neuron_count_half && j < Neuron_count))
  238. {
  239. sigma[i][j] = sigma_N;
  240. }
  241. }
  242. }
  243. }
  244.  
  245. void FillRandomMatrix()
  246. {
  247. for (int k = 0; k < 2 * Neuron_count_half; k++)
  248. {
  249. int i, j;
  250.  
  251. do
  252. {
  253. i = RandomI(Neuron_count_half, Neuron_count);
  254. j = RandomI(Neuron_count_half, Neuron_count);
  255. } while ((i == j) || (A[i][j] == 1));
  256.  
  257. A[i][j] = 1;
  258. A[j][i] = 1;
  259. }
  260. }
  261.  
  262. int main(int argc, char *argv[])
  263. {
  264. FILE *fp0;
  265. srand(time(NULL));
  266.  
  267. A = malloc(Neuron_count * sizeof(double));
  268. for (int i = 0; i < Neuron_count; i++)
  269. A[i] = malloc(Neuron_count * sizeof(double));
  270.  
  271. B = malloc(Neuron_count * sizeof(double));
  272. for (int i = 0; i < Neuron_count; i++)
  273. B[i] = malloc(Neuron_count * sizeof(double));
  274.  
  275. C = malloc(Neuron_count * sizeof(double));
  276.  
  277. sigma = malloc(Neuron_count * sizeof(double));
  278. for (int i = 0; i < Neuron_count; i++)
  279. sigma[i] = malloc(Neuron_count * sizeof(double));
  280.  
  281. FillAMatrixZero();
  282. FillRandomMatrix();
  283. FillBCMatrix();
  284. FillSigmaMatrix();
  285.  
  286. fp0 = fopen("A.txt", "w+");
  287. for (int i = 0; i < Neuron_count; i++)
  288. {
  289. for (int j = 0; j < Neuron_count; j++)
  290. {
  291. fprintf(fp0, "%d\t", (int)A[i][j]);
  292. }
  293. fprintf(fp0, "\n");
  294. }
  295. fclose(fp0);
  296.  
  297. //Пишем в файл число связей у каждого осциллятора в четвертом квадранте
  298. fp0 = fopen("links.txt", "w+");
  299. for (int i = Neuron_count_half; i < Neuron_count; i++)
  300. {
  301. int links_count = 0;
  302. for (int j = Neuron_count_half; j < Neuron_count; j++)
  303. {
  304. if (A[i][j] == 1)
  305. {
  306. links_count++;
  307. }
  308. }
  309. fprintf(fp0, "%d\n", (int)links_count);
  310.  
  311. }
  312. fclose(fp0);
  313.  
  314. fp0 = fopen("B.txt", "w+");
  315.  
  316. for (int i = 0; i < Neuron_count; i++)
  317. {
  318. for (int j = 0; j < C[i]; j++)
  319. {
  320. fprintf(fp0, "%d\t", (int)B[i][j]);
  321. }
  322. fprintf(fp0, "\n");
  323. }
  324.  
  325. fclose(fp0);
  326.  
  327. fp0 = fopen("C.txt", "w+");
  328.  
  329. for (int i = 0; i < Neuron_count; i++)
  330. {
  331. fprintf(fp0, "%d\n", (int)C[i]);
  332. }
  333.  
  334. fclose(fp0);
  335.  
  336. fp0 = fopen("sigma.txt", "w+");
  337. for (int i = 0; i < Neuron_count; i++)
  338. {
  339. for (int j = 0; j < Neuron_count; j++)
  340. {
  341. fprintf(fp0, "%f\t", sigma[i][j]);
  342. }
  343. fprintf(fp0, "\n");
  344. }
  345.  
  346. fclose(fp0);
  347.  
  348. // Initial values
  349. for (int i = 0; i < Equations_count; i++)
  350. {
  351. f[i] = 0;
  352. }
  353.  
  354. for (int i = 0; i < Equations_count; i++)
  355. {
  356. I_app[i] = RandomD(10, 50);
  357. }
  358.  
  359. const double t_start = 0;
  360. const double t_max = 500;
  361. const double dt = 0.01;
  362.  
  363. double t = t_start;
  364.  
  365. fp0 = fopen("results.txt", "w+");
  366. //setlocale(LC_NUMERIC, "French_Canada.1252");
  367.  
  368. clock_t start_rk4, end_rk4;
  369. start_rk4 = clock();
  370. int lastPercent = -1;
  371.  
  372. while (t < t_max || Approximately(t, t_max))
  373. {
  374. fprintf(fp0, "%f\t", t);
  375.  
  376. for (int i = 0; i < Equations_count; i += 4)
  377. fprintf(fp0, i == Equations_count - 1 ? "%f" : "%f\t", f[i]);
  378.  
  379. fprintf(fp0, "\n");
  380.  
  381. double f_next[Equations_count];
  382.  
  383. RungeKutta(dt, f, f_next);
  384. CopyArray(f_next, f, Equations_count);
  385.  
  386. t += dt;
  387.  
  388. int percent = (int)(100 * (t - t_start) / (t_max - t_start));
  389. if (percent != lastPercent)
  390. {
  391. printf("Progress: %d%%\n", percent);
  392. lastPercent = percent;
  393. }
  394. }
  395.  
  396. fclose(fp0);
  397.  
  398. end_rk4 = clock();
  399. double extime_rk4 = (double)(end_rk4 - start_rk4) / CLOCKS_PER_SEC;
  400. int minutes = (int)extime_rk4 / 60;
  401. int seconds = (int)extime_rk4 % 60;
  402. printf("\nExecution time is: %d minutes %d seconds\n ", minutes, seconds);
  403.  
  404. fp0 = fopen("time_exec.txt", "w+");
  405. fprintf(fp0, "%f\n", extime_rk4);
  406. fclose(fp0);
  407.  
  408. for (int i = 0; i < Neuron_count; i++)
  409. free(A[i]);
  410. free(A);
  411.  
  412. for (int i = 0; i < Neuron_count; i++)
  413. free(B[i]);
  414. free(B);
  415.  
  416. for (int i = 0; i < Neuron_count; i++)
  417. free(sigma[i]);
  418. free(sigma);
  419.  
  420. free(C);
  421. }
Advertisement
Add Comment
Please, Sign In to add comment