summaryrefslogblamecommitdiffstats
path: root/fiz/naloga/numerično.c
blob: e10289912cc51f8982f6695759ff6d56a20036f3 (plain) (tree)






























































































































































                                                                                                      
#include <stdlib.h>
#include <stdio.h>
#include <error.h>
#include <math.h>
#define UVOD "program za numerični izračun jakosti magnetnega polja okoli helmholtzove tuljave\n" \
	"sem spisal anton luka šijanec za projektno nalogo pri fiziki v tretjem letniku gimb.\n" \
	"uporaba: %s	in argumenti po vrsti:\n" \
	"	1. radij enega navitja v metrih\n" \
	"	2. tok, ki teče po vodniku v amperih\n" \
	"	3. število navojev na enem navitju\n" \
	"	4. razmak med merilnimi točkami v metrih\n" \
	"	5. koliko meritev od središča v obe dimenziji naj napravimo\n" \
	"	6. koliko kotov naj ima navitje - računamo, kot da je mnogokotnik\n" \
	"	7. tip izhodnih podatkov (pgm ali csv)\n" \
	"oblika izhodnih podatkov, če je 7. parameter pgm, so pgm slike z vrednostmi 0-255\n" \
	"	- slika je prerez tuljave. magnetno polje teče vodoravno.\n" \
	"	- vrednosti direktno korelirajo z izračunano jakostjo v decigaussih: 10e-5 tesla\n" \
	"	- slika je široka 1+2*koliko in visoka 1+2*koliko (5. argument) slikovnih točk\n" \
	"oblika izhodnih podatkov, če je 7. parameter csv, je csv, z naslednjimi stolpci:\n" \
	"	1. vodoravna komponenta oddaljenosti od središča tuljave v metrih\n" \
	"	2. navpična komponenta oddaljenosti od središča tuljave v metrih\n" \
	"	3. jakost magnetnega polja v teslah - tokrat ni v decigaussih!\n" \
	"	4. smer vektorja magnetnega polja v radianih. 0 radianov je smer v desno"
enum oblika {
	PGM,
	CSV
};
struct vektor {
	long double i; // x - desno na sliki
	long double j; // y - gor na sliki
	long double k; // z - v monitor
};
struct vektor seštej (struct vektor a, struct vektor b) {
	struct vektor r = {
		.i = a.i + b.i,
		.j = a.j + b.j,
		.k = a.k + b.k,
	};
	return r;
}
struct vektor vektorski_produkt (struct vektor a, struct vektor b) {	// ne bom implementiral
	struct vektor r = {						// matrik
		.i = a.j*b.k - a.k*b.j,
		.j = a.k*b.i - a.i*b.k,
		.k = a.i*b.j - a.j*b.i
	};
	return r;
}
struct vektor množi (struct vektor a, long double d) {
	struct vektor r = {
		.i = a.i * d,
		.j = a.j * d,
		.k = a.k * d
	};
	return r;
}
long double absolutno (struct vektor a) {
	return sqrtl(a.i*a.i+a.j*a.j+a.k*a.k);
}
#define MU0 4e-6*M_PI
struct vektor tuljava (long double R,	unsigned kotov, struct vektor m /* meritev - krajevni */) {
	long double dl_abs = 2*M_PI*R/kotov;	// metri - dolžina vodnika
	long double dr = 2*M_PI/kotov;		// radiani - kot med dl in točko na (0,R - vrh zanke)
	struct vektor B = {
		.i = 0,
		.j = 0,
		.k = 0
	};
	for (unsigned i = 0; i < kotov; i++) {
		long double theta = dr*i;	// kot na krogu
		struct vektor dl;
		dl.j = cosl(theta)*dl_abs;
		dl.k = -sinl(theta)*dl_abs;	// minus po skici sodeč ://of.sijanec.eu/sfu/skic.jpg
		dl.i = 0;			// sicer je vseeno, m je na z = 0 in gledamo vse
		struct vektor r;
		r.i = 0;
		r.j = sinl(theta)*R;
		r.k = cosl(theta)*R;
		r = seštej(r, m);
		B =	seštej(B,
				množi(
					vektorski_produkt(dl, r),
					1/(absolutno(r)*absolutno(r)*absolutno(r))
				)
			);
	}
	B = množi(B, MU0/(4*M_PI));
	return B;
} // ena zanka ob toku 1 A. pomnoži s tokom in številom navitij. 0,0 je v sredini. B teče v desno.
void natisni (FILE * f, struct vektor v, const char * i) {
	fprintf(f, "vektor %s {\n\t.i = %Lf,\n\t.j = %Lf,\n\t.k = %Lf\n}\n", i, v.i, v.j, v.k);
}
int main (int argc, char ** argv) {
	if (argc != 1 + 7)
		error(1, 0, UVOD, argv[0] ? argv[0] : "./numerično");
	long double R = strtold(argv[1], NULL);
	long double I = strtold(argv[2], NULL);
	unsigned n = strtol(argv[3], NULL, 10);
	long double razmak = strtold(argv[4], NULL);
	int koliko = strtold(argv[5], NULL);
	unsigned kotov = strtol(argv[6], NULL, 10);
	enum oblika oblika = argv[7][0] == 'p' || argv[7][0] == 'P' ? PGM : CSV;
	struct vektor merilno_mesto = {	// krajevni vektor
		.k = 0
	};
	if (oblika == CSV)
		error(2, 0, "CSV oblika še ni implementirana.");
	printf("P5 %u %u 255\n", koliko*2+1, koliko*2+1);
	struct vektor Rpolovic = {
		.i = R/2,
		.j = 0,
		.k = 0
	};
	for (int i = -koliko; i <= koliko; i++) {
		merilno_mesto.i = i*razmak;
		for (int j = -koliko; j <= koliko; j++) {
			merilno_mesto.j = j*razmak;
			unsigned long long int out =
				1000*absolutno(seštej(
					množi(
						množi(
							tuljava(
								R,
								kotov,
								seštej(
									merilno_mesto,
									Rpolovic
								)
							),
							n
						),
						I
					),
					množi(
						množi(
							tuljava(
								R,
								kotov,
								seštej(
									merilno_mesto,
									množi(
										Rpolovic,
										-1
									)
								)
							),
							n
						),
						I
					)
				));
			if (out > 255)
				putchar(255);
			else
				putchar(out);
		}
	}
	return 0;
}