Menu
Coddy logo textTech

תבנית הורס

חלק מהיחידה תכנות מונחה עצמים במסלול ה-C של Coddy. שיעור 13 מתוך 61.

יש לשחרר בסופו של דבר כל אובייקט שנוצר באמצעות malloc. בדיוק כפי שכתבנו פונקציית create_ לטיפול בהקצאה, אנחנו כותבים פונקציית free_ לטיפול בניקוי. זוהי תבנית ההורס.

התובנה המרכזית היא שהשחרור חייב להתבצע בסדר הפוך לסדר ההקצאה. אם הבנאי שלך הקצה תחילה את האיברים הפנימיים ואז את המבנה עצמו, המשמיד שלך חייב לשחרר תחילה את איברי המבנה, ואז את המבנה:

typedef struct {
    char *name;
    int age;
} Person;

void free_person(Person *p) {
    if (p == NULL) return;  // בדיקת בטיחות
    free(p->name);          // תחילה יש לשחרר את השדה הפנימי
    free(p);                // לאחר מכן יש לשחרר את ה-struct עצמו
}

הבדיקה של NULL בתחילת הפונקציה מונעת קריסות אם מישהו מעביר בטעות מצביע לא תקין. אחרי שמשחררים את מחרוזת ה־name הפנימית, משחררים את המבנה עצמו. אם היינו משחררים קודם את p, היינו מאבדים את הגישה ל־p->name וגורמים לדליפת זיכרון.

השימוש בהורס פשוט:

Person *alice = create_person("Alice", 30);
// ... השתמשו ב-alice ...
free_person(alice);  // שחררו משאבים בסיום

התבנית הזאת מבטיחה שכל הזיכרון ישוחרר כראוי. בלעדיה, כל אובייקט שתיצור יגרום לדליפת זיכרון עד שהתוכנית שלך תיגמר בו.

challenge icon

אתגר

קל

נבנה מודול Movie שמדגים את מחזור החיים המלא של אובייקט: גם יצירה וגם השמדה. תתרגלו לכתוב פונקציית הרס שמשחררת כראוי את כל הזיכרון שהוקצה, בסדר הנכון.

תיצרו שלושה קבצים:

  • movie.h: הצהירו על מבנה Movie עם שני איברים: char *title (מחרוזת שהוקצה לה זיכרון באופן דינמי) ו-int year. הצהירו על בנאי create_movie שמקבל כותרת ושנה, ועל פונקציית הרס free_movie שמקבלת מצביע ל-Movie. השתמשו במשמרות הכללה עם הסמל MOVIE_H.
  • movie.c: ממשו את שתי הפונקציות. הבנאי שלכם צריך להקצות זיכרון למבנה ולמחרוזת הכותרת שלו (אל תשכחו את תו הסיום null). פונקציית ההרס חייבת לשחרר את הזיכרון בסדר הפוך לסדר ההקצאה: תחילה את מחרוזת ה-title הפנימית, ולאחר מכן את המבנה עצמו. הוסיפו בדיקת NULL בתחילת פונקציית ההרס, ליתר ביטחון.
  • main.c: צרו סרט, הציגו את המידע שלו, ואז שחררו כראוי את הזיכרון.

תקבלו שני קלטים: כותרת הסרט (מחרוזת) ושנת ההפצה (מספר שלם).

בקובץ הראשי שלכם, השתמשו ב-create_movie כדי ליצור סרט חדש, הדפיסו את המידע שלו, ואז קראו ל-free_movie כדי לשחרר את כל הזיכרון. לאחר השחרור, הדפיסו הודעת אישור.

הדפיסו את הפלט בפורמט הזה:

Movie: {title} ({year})
Memory freed

לדוגמה, עבור הקלטים Inception ו-2010, הפלט יהיה:

Movie: Inception (2010)
Memory freed

זכרו: המפתח לפונקציית הרס תקינה הוא שחרור בסדר הפוך. מה שהבנאי שלכם מקצה ראשון משתחרר אחרון, ומה שהוא מקצה אחרון משתחרר ראשון.

נסו בעצמכם

#include <stdio.h>
#include <stdlib.h>
#include "movie.h"

int main() {
    char title[100];
    int year;
    
    // קרא את הקלט
    scanf("%[^\n]", title);
    scanf("%d", &year);
    
    // TODO: צור סרט באמצעות create_movie
    
    // TODO: הדפס את פרטי הסרט בפורמט:
    // סרט: {title} ({year})
    
    // TODO: שחרר את הזיכרון של הסרט באמצעות free_movie
    
    // TODO: הדפס "Memory freed"
    
    return 0;
}
quiz iconבחנו את עצמכם

השיעור הזה כולל חידון קצר. התחילו את השיעור כדי לענות עליו ולעקוב אחרי ההתקדמות.

כל השיעורים ביחידה תכנות מונחה עצמים

תרגלו בעצמכם: קומפיילר C אונליין