Advertisement
Aurox_

bethe-1

May 29th, 2025
359
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 5.72 KB | Science | 0 0
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4. #include <math.h>
  5.  
  6. #define STRLEN  1024
  7. #define ARGNUM  4       /* ./executable <initial_energy> <thickness> <steps> <output_file> */
  8. #define MAX_ATTEMPTS 3
  9.  
  10. #define ERR         -1
  11. #define ERR_ARGC    1
  12. #define ERR_FILE    2
  13.  
  14. #define ME      0.511   /* mass of electron in MeV / c^2 */
  15. #define K       0.307   /* constant K in Bethe--Bloch's formula */
  16.  
  17. #define ALUMINUM 1
  18. #define AL_Z 13
  19. #define AL_A 27
  20. #define AL_R 2.7
  21. #define AL_I 166 /* eV */
  22.  
  23. #define COPPER 2
  24. #define CU_Z 29
  25. #define CU_A 63
  26. #define CU_R 8.96
  27. #define CU_I 322 /* eV */
  28.  
  29. #define PROTON 1
  30. #define PROTON_Z 1
  31. #define PROTON_M 938.272 /* MeV/c^2 */
  32.  
  33. #define ALPHA 2
  34. #define ALPHA_Z 2
  35. #define ALPHA_M 3727.379 /* MeV/c^2 */
  36.  
  37. #define MUON 3
  38. #define MUON_Z -1
  39. #define MUON_M 105.658 /* MeV/c^2 */
  40.  
  41. typedef struct material {
  42.     int id;
  43.     unsigned z;     /* atomic number */
  44.     unsigned a;     /* atomic mass */
  45.     double r;       /* density in g/cm^3 */
  46.     double i;       /* mean excitation energy in eV */
  47. } material_t;
  48.  
  49. typedef struct particle {
  50.     int id;
  51.     unsigned z;     /* charge */
  52.     double m;       /* mass in MeV / c^2 */
  53.     double t;       /* kinetic energy in MeV */
  54. } particle_t;
  55.  
  56. typedef FILE file_t;
  57.  
  58. int myexit(const int status, const char *message) {
  59.     switch (status) {
  60.         case ERR_ARGC:
  61.             fprintf(stderr, "! Error: Incorrect number of arguments.\n");
  62.             fprintf(stderr, "! Usage: %s <initial_energy(MeV)> <steps> <thickness> <output_file>\n", message);
  63.             return status;
  64.         case ERR_FILE:
  65.             fprintf(stderr, "! Error: Could not open output file at '%s'.\n", message);
  66.             return status;
  67.         default:
  68.             fprintf(stderr, "! Error: An error occurred.\n");
  69.             if (message) fprintf(stderr, "! Message: %s\n", message);
  70.             fprintf(stderr, "! Exiting with code: %d\n", status);
  71.             return status;
  72.     }
  73. }
  74.  
  75. int input_target_material(material_t *ptr_material) {
  76.     int choice;
  77.     char buffer[STRLEN];
  78.  
  79.     fprintf(stdout, "Choose target material:\n");
  80.     fprintf(stdout, "1. Aluminum\n");
  81.     fprintf(stdout, "2. Copper\n");
  82.     fprintf(stdout, "Enter choice (1 or 2): ");
  83.  
  84.     if (fgets(buffer, STRLEN, stdin) == NULL) return 1;
  85.     choice = atoi(buffer);
  86.  
  87.     switch (choice) {
  88.         case ALUMINUM:
  89.             ptr_material->id = ALUMINUM;
  90.             ptr_material->z = AL_Z;
  91.             ptr_material->a = AL_A;
  92.             ptr_material->r = AL_R;
  93.             ptr_material->i = AL_I;
  94.             return 0;
  95.         case COPPER:
  96.             ptr_material->id = COPPER;
  97.             ptr_material->z = CU_Z;
  98.             ptr_material->a = CU_A;
  99.             ptr_material->r = CU_R;
  100.             ptr_material->i = CU_I;
  101.             return 0;
  102.         default:
  103.             return 1;
  104.     }
  105. }
  106.  
  107. int input_projectile(particle_t *ptr_projectile) {
  108.     int choice;
  109.     char buffer[STRLEN];
  110.  
  111.     fprintf(stdout, "Choose projectile:\n");
  112.     fprintf(stdout, "1. Proton\n");
  113.     fprintf(stdout, "2. Alpha particle\n");
  114.     fprintf(stdout, "3. Muon\n");
  115.     fprintf(stdout, "Enter choice (1, 2 or 3): ");
  116.  
  117.     if (fgets(buffer, STRLEN, stdin) == NULL) return 1;
  118.     choice = atoi(buffer);
  119.  
  120.     switch (choice) {
  121.         case PROTON:
  122.             ptr_projectile->id = PROTON;
  123.             ptr_projectile->z = PROTON_Z;
  124.             ptr_projectile->m = PROTON_M;
  125.             return 0;
  126.         case ALPHA:
  127.             ptr_projectile->id = ALPHA;
  128.             ptr_projectile->z = ALPHA_Z;
  129.             ptr_projectile->m = ALPHA_M;
  130.             return 0;
  131.         case MUON:
  132.             ptr_projectile->id = MUON;
  133.             ptr_projectile->z = MUON_Z;
  134.             ptr_projectile->m = MUON_M;
  135.             return 0;
  136.         default:
  137.             return 1;
  138.     }
  139. }
  140.  
  141. double wmax(double beta2, double gamma, double gamma2, double m, double m2) {
  142.     return (2.0 * ME * beta2 * gamma2) / (1.0 + (2.0 * gamma * m) + m2);
  143. }
  144.  
  145. double bethe(double z_inc, double z_tar, double a_tar, double beta2, double gamma2, double w_max, double i) {
  146.     return (((K * z_inc * z_inc * z_tar) / (a_tar * beta2)) * (0.5 * log((2.0 * ME * beta2 * gamma2 * w_max) / (i * i * 1.0e-12)) - beta2));
  147. }
  148.  
  149. int main(int argc, char *argv[]) {
  150.     /* char        buffer[STRLEN]; */
  151.     int         steps, i, attempts;
  152.     double      thickness, initial_energy;
  153.     file_t     *ptr_file_out;
  154.     material_t  target;
  155.     particle_t  projectile;
  156.  
  157.     if (argc != ARGNUM + 1) return myexit(ERR_ARGC, argv[0]);
  158.  
  159.     initial_energy = atof(argv[1]);
  160.     thickness      = atof(argv[2]);
  161.     steps          = atoi(argv[3]);
  162.     ptr_file_out   = fopen(argv[4], "w");    
  163.    
  164.     if (initial_energy <= 0)    return myexit(ERR, "Kinetic energy must be positive.");
  165.     if (steps          <= 0)    return myexit(ERR, "Number of steps must be positive.");
  166.     if (thickness      <= 0)    return myexit(ERR, "Thickness must be positive.");
  167.     if (ptr_file_out   == NULL) return myexit(ERR_FILE, argv[4]);
  168.    
  169.     for (attempts = 0; attempts < MAX_ATTEMPTS; attempts++) {
  170.         if (attempts >= 1) fprintf(stdout, "! Try again. Attempt: %d/%d\n", attempts + 1, MAX_ATTEMPTS);
  171.         if (!input_target_material(&target)) break;
  172.         if (attempts == (MAX_ATTEMPTS - 1)) return myexit(ERR, "Too many attempts at input material.");
  173.     }
  174.  
  175.     for (attempts = 0; attempts < MAX_ATTEMPTS; attempts++) {
  176.         if (attempts >= 1) fprintf(stdout, "! Try again. Attempt: %d/%d\n", attempts + 1, MAX_ATTEMPTS);
  177.         if (!input_projectile(&projectile)) break;
  178.         if (attempts == (MAX_ATTEMPTS - 1)) return myexit(ERR, "Too many attempts at input projectile.");
  179.     }
  180.  
  181.     fclose(ptr_file_out);
  182.     return 0;
  183. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement