Generic selectors
Exact matches only
Search in title
Search in content
Post Type Selectors

המדריך לתכנות מקבילי בשפת C Sharp – פרק ט' – Thread Pool

Thread Pool בשפת #C הוא מעין מאגר שמחזיק בתוכו Threads שניתן לשלוף ולאחסן בהתאם לצרכי התוכנית שלנו ובכך לחסוך במשאבי זיכרון. בפרק זה של המדריך נדגים כיצד ניתן לעשות זאת.

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

אורך החיים של מופע ה-Thread

ראשית עלינו להבין את מחזור החיים של מופע ה-Thread.
שימו לב לתרשים הזרימה הבא:

Multithreading - Thread Life Cycle
Multithreading – Thread Life Cycle

כלומר שאם נרצה לתאר זאת במילים נוכל לכתוב כך:

  1. נשלחת בקשה מסוימת בתוכנית שלנו
  2. נוצר Thread חדש שיצרנו על מנת לנהל בקשה זו
  3. ה-Thread יאסוף את המשאבים שאיתם הוא הולך לעבוד
  4. הבקשה תטופל על ידי ה-Thread
  5. ה-Thread "יסולק" מהזיכרון על ידי אוסף הזבל

 

צעדים אלו יחזרו על עצמם שוב ושוב עבור כל בקשה שנשלחת בתוכנית שמשתמשת ב-Threads רבים.
כלומר שבכל פעם שאנו יוצרים מופע של Thread, מוגדרת עבורו כתובת בזיכרון,
מה שגם אומר שהוא "תופס" מקום מסוים בזיכרון (הוקצו עבורו משאבי זיכרון).
אם כך, חישבו על מצב שבו נוצרים Threads רבים בו-זמנית בתוכנית שלנו –
מצב כזה יכול לפגוע בביצועי התוכנית ולגרום להאטה בתוכנית.

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

Thread Pool

Thread Pool הוא למעשה מעין מאגר שמחזיק בתוכו Threads שניתן לשלוף ולאחסן בהתאם לצרכים שלנו.
כאשר אנו משתמשים בו, מחזור החיים של מופע ה-Thread ישתנה.
נוכל בתום הטיפול בבקשה להעביר את מופע ה-Thread למאגר,
ובכך אוסף הזבל לא ינקה אותו בתום השימוש:

Multithreading - Thread Life Cycle
Multithreading – Thread Life Cycle

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

Multithreading - Thread Life Cycle
Multithreading – Thread Life Cycle

מחלקת ThreadPool

על מנת שנוכל לבצע Thread Pooling נשתמש במתודה הסטטית QueueUserWorkItem:

ThreadPool.QueueUserWorkItem(new WaitCallback(MyMethod));

  • כתוצאה מכך שאנו מייבאים את System.Threading – נוכל להשתמש במחלקת ThreadPool.
  • כפרמטר מתודה זו מקבלת אובייקט WaitCallback.
  • כאשר אנו יוצרים אובייקט WaitCallback נשלח לו כפרמטר את המתודה הרצויה
  • מדובר בדלגאט, ובמקרה הזה הדלגאט מצפה לקבל מתודה שמקבלת Object כפרמטר, אחרת נקבל שגיאה.

 

שימו לב ל-Code Snippet הבא אשר יבאר נושא זה:

using System.Threading;

namespace ThreadPooling
{
    public class Program
    {
        public static void Main()
        {

            for (int i = 0; i < 10; i++)
            {
                ThreadPool.QueueUserWorkItem(new WaitCallback(MyMethod));
            }
            Console.Read();
        }

        public static void MyMethod(object obj)
        {
            Thread thread = Thread.CurrentThread;
            string message = $"Is Background Thread: {thread.IsBackground}, Is ThreadPool Thread: {thread.IsThreadPoolThread}, Thread ID: {thread.ManagedThreadId}";
            Console.WriteLine(message);
        }
    }
}

בתוכנית זו למעשה השתמשנו ב-Thread Pooling על מנת להמחיש את אופן הפעולה שדובר לפני,
במקום שכל פעם ניצור מופע של Thread מסוים, שלפנו והחזרנו את ה-Thread בכל פעם אל ה-Thread Pool.

*אם נרצה למשל לסיים באופן מיידי את עבודתו של Thread כלשהו, נוכל להשתמש במתודה Abort.

לסיכום ניתן לומר כי Multithreading הוא נושא עמוק וחשוב מאין כמוהו,
אשר באמצעות שימוש בו נוכל לנהל ולסנכרן את התוכנית שלנו בצורה יעילה.

לקריאה מורחבת על Thread ו-Threading באתר של מייקרוסופט יש ללחוץ כאן.

רוצים לשתף את המדריך?

אהבתכם את המדריך? פתר לכם תקלה? הזמינו את כותב המדריך לכוס קפה

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

ניתן לתרום 10, 15, 20 או כל סכום אחר שתרצו באמצעות כרטיס אשראי \ Paypal

כתיבת תגובה

האימייל לא יוצג באתר. שדות החובה מסומנים *

הזמינו אותי לכוס קפה
buy me coffee

אהבתכם את המדריך? פתר לכם תקלה? הזמינו את כותב המדריך לכוס קפה

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