1. ما هو def
في بايثون؟
تُستخدم الكلمة المفتاحية def
في بايثون لتعريف الدوال. الدوال هي هياكل أساسية لزيادة إمكانية إعادة استخدام الكود وجعل البرامج أكثر تنظيماً. باستخدام def
، يمكنك إنشاء كتلة من الكود لأداء مهمة معينة واستخدامها بشكل متكرر. هذا يحسن من وضوح الكود ويقلل من معدل الأخطاء البرمجية.
البنية الأساسية لكلمة def
البنية الأساسية كما يلي:
def اسم_الدالة(المعامل1, المعامل2, ...):
معالجة
return قيمة_الإرجاع
بعد def
، يتم كتابة اسم الدالة وتحديد المعاملات اللازمة بين الأقواس. ثم، بعد النقطتين، تكتب محتوى الدالة باستخدام مسافة بادئة (indentation). يمكن استخدام جملة return
لإرجاع قيمة إذا لزم الأمر.
2. البنية الأساسية واستخدام def
كيفية تعريف دالة أساسية
عند تعريف دالة باستخدام def
، يجب تحديد اسم الدالة وقائمة المعاملات ومحتوى المعالجة. على سبيل المثال، الكود التالي يُعرّف دالة تقوم بطباعة “Hello, World!”:
def say_hello():
print("Hello, World!")
يمكنك استدعاء هذه الدالة بكتابة say_hello()
، وسيتم طباعة “Hello, World!” في وحدة التحكم.
أهمية المسافة البادئة (Indentation)
المسافة البادئة مهمة جداً في بايثون. يجب كتابة جميع الكود داخل الدالة بنفس مستوى المسافة البادئة. تُستخدم المسافة البادئة لتحديد البنية الهيكلية للكود، وأي خطأ فيها قد يؤدي إلى ظهور أخطاء برمجية.
استدعاء الدوال
يمكن استدعاء الدوال المُعرفة بإضافة اسم الدالة متبوعاً بالأقواس. إذا كان هناك معاملات، يتم تمريرها داخل الأقواس.
say_hello()
3. معاملات الدوال والقيم الافتراضية
المعاملات الموضعية والمعاملات المسماة
يمكن للدوال أن تأخذ معاملات، وتنقسم هذه المعاملات إلى معاملات موضعية (يتم تمريرها حسب الترتيب) ومعاملات مسماة (يتم تمريرها مع اسمها).
def greet(name, greeting="Hello"):
print(f"{greeting}, {name}!")
في المثال أعلاه، تم تعيين قيمة افتراضية لـ greeting
، وعند استدعاء greet("Alice")
سيتم طباعة “Hello, Alice!”.
المعاملات متعددة القيم
أحياناً، قد تحتاج دالة إلى استقبال عدد غير محدد من المعاملات. في بايثون، يمكن استخدام *args
و **kwargs
لذلك.
def print_args(*args):
for arg in args:
print(arg)
print_args(1, 2, 3)
في هذا المثال، *args
يستقبل جميع القيم كـ tuple.
4. إرجاع القيم باستخدام جملة return
كيفية استخدام return
إذا كنت تريد أن تُرجع الدالة قيمة ما، استخدم جملة return
. إذا لم يتم استخدام return
، سترجع الدالة القيمة الافتراضية None
.
def add(a, b):
return a + b
result = add(3, 4)
print(result) # 7
الدالة add
هنا تُرجع مجموع رقمين. باستخدام return
يمكن حفظ النتيجة في متغير.
إرجاع قيم متعددة
يمكن للدوال في بايثون إرجاع أكثر من قيمة عن طريق الفصل بينها بفاصلة. سيتم إرجاعها كـ tuple.
def swap(a, b):
return b, a
x, y = swap(1, 2)
print(x, y) # 2 1
5. نطاق المتغيرات (Scope) ومدة حياتها (Lifetime)
المتغيرات المحلية والعالمية
المتغيرات المعرفة داخل الدالة تُسمى متغيرات محلية ولا يمكن استخدامها خارج الدالة. أما المتغيرات المعرفة خارج الدوال فهي متغيرات عالمية ويمكن استخدامها في جميع أجزاء البرنامج.
x = "global"
def func():
x = "local"
print(x)
func() # local
print(x) # global
في هذا المثال، x
داخل الدالة func
متغير محلي ولا يؤثر على المتغير العالمي.
كلمة global
إذا أردت تعديل متغير عالمي داخل دالة، استخدم الكلمة المفتاحية global
.
x = "global"
def change_global():
global x
x = "changed"
change_global()
print(x) # changed
6. أمثلة عملية واستخدامات
تحسين كفاءة البرنامج باستخدام الدوال
باستخدام الدوال، يمكنك تحسين كفاءة البرنامج بشكل كبير. على سبيل المثال، يمكن تجميع العمليات المتكررة أو معالجة البيانات داخل دوال لتقليل التكرار في الكود.
def calculate_area(radius):
return 3.14 * radius * radius
area1 = calculate_area(5)
area2 = calculate_area(10)
في هذا المثال، دالة calculate_area
تُستخدم لحساب مساحة الدائرة عدة مرات بسهولة.
أمثلة على استخدام الدوال
مثال آخر هو إنشاء دالة لتنسيق النصوص.
def format_text(text, alignment="left"):
if alignment == "left":
return text.ljust(20)
elif alignment == "right":
return text.rjust(20)
elif alignment == "center":
return text.center(20)
print(format_text("Hello", "center"))
هذه الدالة تقوم بتنسيق النص إما لليسار أو اليمين أو للمنتصف.
7. مفاهيم متقدمة حول الدوال
الدوال المتداخلة (Nested Functions)
يمكن تعريف دالة داخل دالة أخرى في بايثون، وتسمى هذه الدوال المتداخلة. الدالة المتداخلة متاحة فقط داخل الدالة الخارجية.
def outer():
def inner():
print("This is the inner function")
inner()
الدوال المجهولة (Lambda)
يمكنك استخدام الكلمة المفتاحية lambda
لإنشاء دوال بدون اسم. وهي مفيدة للعمليات البسيطة والسريعة.
square = lambda x: x * x
print(square(5)) # 25
المزخرفات (Decorators)
المزخرفات (decorators) طريقة لإضافة وظائف إضافية للدوال بدون تعديل الدالة نفسها. يتم تعريفها كدوال تأخذ دوال أخرى كمعاملات وتُرجع دوال جديدة.
def decorator(func):
def wrapper():
print("Before the function")
func()
print("After the function")
return wrapper
@decorator
def say_hello():
print("Hello!")
say_hello()
8. الخلاصة
في هذا المقال، شرحنا كيفية تعريف الدوال باستخدام def
في بايثون، وتناولنا المعاملات وقيم الإرجاع ونطاق المتغيرات، بالإضافة إلى مفاهيم متقدمة. باستخدام الدوال بشكل فعّال، يمكنك بناء برامج أكثر تنظيماً وكفاءة. استعن بهذا المقال لتطوير مهاراتك في بايثون من خلال كتابة دوال متنوعة.
9. الأسئلة المتكررة (FAQs)
ما الفرق بين return
و print
؟
return
و print
لهما وظائف مختلفة. return
يُرجع قيمة من الدالة لاستخدامها في أجزاء أخرى من البرنامج، مثل تخزين نتيجة عملية حسابية. أما print
فيقوم فقط بعرض النتائج على وحدة التحكم ولا يمكن استخدام قيمته في بقية البرنامج.
def add(a, b):
return a + b
result = add(3, 4) # سيتم تخزين 7 في المتغير result
print(result) # 7
def display_message():
print("Hello, World!")
display_message() # سيتم عرض "Hello, World!" في وحدة التحكم فقط
ما هي فوائد استخدام الدوال المتداخلة؟
تسمح لك الدوال المتداخلة بإنشاء دوال محلية لا يمكن الوصول إليها من الخارج، مما يعزز تنظيم الكود وإعادة استخدامه. كما يمكنها الوصول إلى نطاق الدالة الخارجية لتسهيل بعض المعالجات الخاصة.
متى يجب استخدام المعاملات متعددة القيم؟
استخدم المعاملات متعددة القيم عندما لا تعرف عدد المعاملات مسبقاً. على سبيل المثال، عند إنشاء دالة تجمع أرقاماً غير محددة.
def add_all(*args):
return sum(args)
result = add_all(1, 2, 3, 4, 5) # 15
كيف أستخدم الدوال العودية (Recursion)؟
الدالة العودية هي دالة تستدعي نفسها. تُستخدم لحل المشاكل التي يمكن تقسيمها بشكل متكرر، مثل حساب المضروب (factorial)، ولكن يجب استخدامها بحذر لتجنب مشاكل تجاوز الحد الأقصى للتكرار (stack overflow).
def factorial(n):
if n == 0:
return 1
else:
return n * factorial(n-1)
result = factorial(5) # 120