تطوير برنامج لحل المعادلات الخطية باستخدام Gauss Elimination

مقدمة

الأنظمة الخطية Linear Systems تظهر بكل مكان:

  • الفيزياء
  • الهندسة
  • الذكاء الاصطناعي
  • تعلم الآلة
  • المعادلات التفاضلية
  • الإلكترونيات
  • الاقتصاد
  • أنظمة التوقع
  • تحليل الشبكات
  • البرمجة الهندسية
  • أي نموذج رياضي متقدم

وأشهر طريقة لحل نظام معادلات خطي هو:

Gaussian Elimination
(الحذف الغاوسي)

هذه الطريقة تعتبر العمود الفقري للجبر الخطي الحديث، وهي الأساس لأغلب الخوارزميات المتقدمة (LU Decomposition، QR، SVD…).

اليوم رح نكتب برنامج كامل لحل الأنظمة الخطية باستخدام Gauss Elimination.


ما هو النظام الخطي؟

مثال:

2x + 3y -   z =  5
4x +   y + 5z =  6
 -x + 2y + 3z = 10

هذا نظام مكوّن من ثلاث معادلات وثلاث مجاهيل.

نكتبه كمصفوفة موسّعة Augmented Matrix:

[ 2   3  -1 |  5 ]
[ 4   1   5 |  6 ]
[-1   2   3 | 10 ]

Gauss Elimination يقوم بتحويل هذه المصفوفة إلى شكل مثل:

[ 1   *   * | * ]
[ 0   1   * | * ]
[ 0   0   1 | * ]

وبعدين نرجع نحسب الحل باستخدام Back Substitution.


الفكرة الأساسية لـ Gaussian Elimination

العملية هي ثلاث مراحل:

1) Forward Elimination

تحويل المصفوفة إلى Upper Triangular Matrix:

  • اجعل العناصر تحت القطر الرئيسي = صفر
  • باستخدام عمليات صفية Elementary Row Operations

2) Pivoting

اختيار صف مناسب لمنع القسمة على صفر
وتقليل الخطأ العددي.

3) Back Substitution

بعد ما نحصل على الشكل:

a11 a12 a13 | b1
0   a22 a23 | b2
0   0   a33 | b3

عندها:

z = b3 / a33
y = (b2 - a23*z)/a22
x = (b1 - a12*y - a13*z)/a11

تفاصيل الخطوات بشكل موسّع

الخطوة الأولى: اختيار Pivot

عند العمود رقم i:

  • نبحث عن الصف الذي يحتوي على أكبر قيمة مطلقة تحت pivot
  • نبدّل الصف الأعلى معه (Row Swap)

هذا يُسمى Partial Pivoting
ويحسن الدقة ويمنع الانهيار العددي.


الخطوة الثانية: تصفير العناصر تحت الـ Pivot

مثال:

لو pivot هو a[i][i]

نريد:

a[j][i] = 0    لكل j > i

نستخدم:

factor = a[j][i] / a[i][i]
row[j] = row[j] - factor * row[i]

الخطوة الثالثة: Back Substitution

بعد ما يصبح الشكل:

[ x    y    z | b ]
[ 0   y1   z1 | b1 ]
[ 0    0    z2 | b2 ]

نبدأ من الأسفل:

z = b2 / z2
y = (b1 - z1*z) / y1
x = (b - y - z) / pivot

الحالات الخاصة (يجب على البرنامج اكتشافها)

1) لا يوجد حل → inconsistent system

مثال:

0x + 0y + 0z = 5

مستحيل.

2) عدد لانهائي من الحلول

مثال:

0x + 0y + 0z = 0

هذا يعني أن النظام ناقص رتبة (rank deficient).

3) القسمة على صفر عند pivot

إذا pivot = 0
→ يجب تبديل الصفوف
→ إذا لم تجد pivot صالح
→ النظام غير قابل للحل أو له حلول لانهائية


الجزء العملي: كتابة برنامج Gauss Elimination بلغة C++

كود احترافي، جاهز للنشر:

#include <iostream>
#include <vector>
#include <cmath>
using namespace std;

const double EPS = 1e-9;

vector<double> gauss(vector<vector<double>> a) {
    int n = a.size();
    int m = a[0].size() - 1;

    for (int i = 0; i < n; i++) {
        // 1) Pivoting
        int pivot = i;
        for (int j = i + 1; j < n; j++) {
            if (fabs(a[j][i]) > fabs(a[pivot][i]))
                pivot = j;
        }

        if (fabs(a[pivot][i]) < EPS)
            continue; // pivot = 0 → skip

        swap(a[i], a[pivot]);

        // 2) Eliminating
        for (int j = i + 1; j < n; j++) {
            double factor = a[j][i] / a[i][i];
            for (int k = i; k <= m; k++)
                a[j][k] -= factor * a[i][k];
        }
    }

    // 3) Back Substitution
    vector<double> x(m, 0);

    for (int i = m - 1; i >= 0; i--) {
        double sum = a[i][m];
        for (int j = i + 1; j < m; j++)
            sum -= a[i][j] * x[j];

        if (fabs(a[i][i]) < EPS) {
            if (fabs(sum) < EPS) {
                cout << "Infinite solutions.\n";
                return {};
            } else {
                cout << "No solution.\n";
                return {};
            }
        }

        x[i] = sum / a[i][i];
    }

    return x;
}

int main() {
    vector<vector<double>> matrix = {
        {2, 3, -1, 5},
        {4, 1, 5, 6},
        {-1, 2, 3, 10}
    };

    vector<double> sol = gauss(matrix);

    cout << "Solutions:\n";
    for (double x : sol)
        cout << x << " ";

    return 0;
}

تحليل الكود

✔ استخدام pivoting لتحسين الدقة
✔ معالجة الأنظمة غير القابلة للحل
✔ اكتشاف عائلة الحلول
✔ تطبيق Back Substitution
✔ التعامل مع قيود EPS لمنع خطأ floating point
✔ إضافة نظام معادلات موسع (Augmented Matrix)
✔ خوارزمية كاملة شاملة لأي n×n


خطورة الدقة العددية Floating Point Errors

طريقة Gaussian Elimination عرضة للأخطاء العددية بسبب:

  • القسمة
  • التراكم
  • rounding
  • subtraction cancellation

لذلك نستخدم:

const double EPS = 1e-9;

لكشف القيم القريبة من الصفر.


التطبيقات الهندسية والرياضية

1) حل المعادلات الكهربائية (Kirchhoff)

2) حل معادلات مقاومات – تيارات – فولتيات

3) تحليل فيزياء الأجسام (Forces)

4) حل الأنظمة الحرارية

5) نمذجة الأنظمة الديناميكية

6) عمليات Machine Learning (نعم! Gauss جزء منها)

7) تحليل بيانات ضخم

8) محاكاة الشبكات

9) تطبيقات الـ Graphics

10) حساب الـ Regression

يعني تعلمك Gauss → قوة جبارة.


أخطاء قاتلة يجب تجنبها

❌ عدم استخدام pivoting → انهيار عدد
❌ تقسيم على صفر
❌ الخطأ في ترتيب الصفوف
❌ التوقف قبل تحويل القطر بالكامل
❌ عدم استخدام EPS
❌ استخدام double بدل long double في الأنظمة الحساسة
❌ عدم فحص الحلول اللانهائية
❌ افتراض أن كل نظام خطي له حل (غلط كبير)


مثال كامل خطوة بخطوة

نفترض النظام:

x + 2y + z =  6
2x + y - z =  3
3x + y + 2z = 10

المصفوفة الموسّعة:

[1  2  1 | 6 ]
[2  1 -1 | 3 ]
[3  1  2 |10 ]

بعد حذف الصفوف يتكون:

[1 2   1 | 6 ]
[0 -3 -3 | -9]
[0  0  1 | 2 ]

Back Substitution:

z = 2
y = (-9 + 3*2) / -3 = 1
x = 6 - 2*1 - 2 = 2

الحل:

x = 2
y = 1
z = 2

الخلاصة النهائية

اليوم تعلمت:

✔ مفهوم الأنظمة الخطية

✔ المصفوفة الموسعة Augmented Matrix

✔ مبدأ Gaussian Elimination

✔ Forward Elimination

✔ Back Substitution

✔ Pivoting وكيفية استخدامه

✔ كشف عدم وجود حل

✔ كشف وجود حلول لانهائية

✔ التعامل مع الدقة العددية

✔ بناء برنامج كامل بلغة C++

✔ تطبيقات هندسية ورياضية ضخمة

هذا درس أساسي لأي شخص يريد الدخول في:

  • علم البيانات
  • الجبر الخطي
  • الذكاء الاصطناعي
  • هندسة الكهرباء
  • المحاكاة Simulations
  • البرمجة العددية
  • تحليل الأنظمة

اكتشاف المزيد من كود التطور

اشترك للحصول على أحدث التدوينات المرسلة إلى بريدك الإلكتروني.

اترك رد

Scroll to Top