数学の知識をプログラムに落とし込む。理工系の計算で頻出のアルゴリズムをC言語で実装します。
#include <stdio.h> #include <math.h> int main(void) { double data[] = {72.5, 85.3, 91.0, 68.2, 77.8, 83.1, 90.5, 65.9}; int n = 8; double sum = 0, sum2 = 0; for (int i = 0; i < n; i++) { sum += data[i]; // 総和 sum2 += data[i] * data[i]; // 二乗和 } double avg = sum / n; double var = sum2 / n - avg * avg; // 分散 = E[X²] - (E[X])² double sd = sqrt(var); printf("データ数: %d\n", n); printf("平均: %.2f\n", avg); printf("分散: %.2f\n", var); printf("標準偏差: %.2f\n", sd); return 0; }
#include <stdio.h> #include <math.h> double f(double x) { return x*x - 2; } // f(x) = x² - 2 double df(double x) { return 2*x; } // f'(x) = 2x int main(void) { double x = 2.0; // 初期値 double EPS = 1e-10; for (int i = 0; i < 100; i++) { double x_new = x - f(x) / df(x); printf("反復%2d: x = %.15f 誤差 = %e\n", i+1, x_new, fabs(x_new - x)); if (fabs(x_new - x) < EPS) break; x = x_new; } printf("√2 ≒ %.15f\n", x); return 0; }
#include <stdio.h> #include <stdlib.h> #include <time.h> int main(void) { int N; printf("試行回数: "); scanf("%d", &N); srand((unsigned)time(NULL)); int inside = 0; for (int i = 0; i < N; i++) { double x = (double)rand() / RAND_MAX; // 0〜1の乱数 double y = (double)rand() / RAND_MAX; if (x*x + y*y <= 1.0) inside++; // 円の内部? } double pi = 4.0 * inside / N; printf("π ≒ %.6f (N=%d)\n", pi, N); printf("真の値: 3.141593\n"); return 0; }
| 試行回数 N | 推定値(例) | 誤差 |
|---|---|---|
| 1,000 | 3.156 | ~0.01 |
| 10,000 | 3.1432 | ~0.001 |
| 100,000 | 3.14052 | ~0.001 |
| 1,000,000 | 3.141284 | ~0.0003 |
| 10,000,000 | 3.141552 | ~0.00004 |
#include <stdio.h> #include <math.h> double f(double x) { return sin(x); } // 被積分関数 // 台形公式 double trapezoid(double a, double b, int n) { double h = (b - a) / n; double sum = (f(a) + f(b)) / 2.0; for (int i = 1; i < n; i++) sum += f(a + i * h); return h * sum; } // シンプソン法(より高精度) double simpson(double a, double b, int n) { double h = (b - a) / n; double sum = f(a) + f(b); for (int i = 1; i < n; i++) sum += (i % 2 == 0) ? 2*f(a+i*h) : 4*f(a+i*h); return h / 3.0 * sum; } int main(void) { printf("∫₀^π sin(x)dx の真の値 = 2.0\n\n"); int ns[] = {10, 100, 1000}; for (int i = 0; i < 3; i++) { printf("n=%4d 台形=%.10f Simpson=%.10f\n", ns[i], trapezoid(0, M_PI, ns[i]), simpson(0, M_PI, ns[i])); } return 0; }
#include <stdio.h> #include <math.h> #define N 3 void gauss(double a[N][N+1], double x[N]) { // 前進消去 for (int i = 0; i < N; i++) { for (int j = i+1; j < N; j++) { double ratio = a[j][i] / a[i][i]; for (int k = i; k <= N; k++) a[j][k] -= ratio * a[i][k]; } } // 後退代入 for (int i = N-1; i >= 0; i--) { x[i] = a[i][N]; for (int j = i+1; j < N; j++) x[i] -= a[i][j] * x[j]; x[i] /= a[i][i]; } } int main(void) { double a[N][N+1] = { { 2, 1, -1, 8}, {-3, -1, 2, -11}, {-2, 1, 2, -3} }; double x[N]; gauss(a, x); for (int i = 0; i < N; i++) printf("x[%d] = %.4f\n", i, x[i]); return 0; // 答え: x=2, y=3, z=-1 }
#include <stdio.h> #include <math.h> double f(double x) { return x*x*x - x - 1; } // x³ - x - 1 = 0 double bisection(double a, double b, double eps) { while (b - a > eps) { double mid = (a + b) / 2.0; if (f(a) * f(mid) <= 0) b = mid; // 根は左半分にある else a = mid; // 根は右半分にある } return (a + b) / 2.0; } int main(void) { double root = bisection(1.0, 2.0, 1e-10); printf("x³ - x - 1 = 0 の根: %.10f\n", root); printf("検算: f(root) = %e\n", f(root)); return 0; }