1. סקירה כללית
בשיעור ה-Lab הזה תלמדו איך לפתח מסווג Keras. במקום לנסות להבין מה השילוב המושלם של שכבות רשת נוירונים לזיהוי פרחים, נשתמש קודם בטכניקה שנקראת למידת העברה (transfer learning) כדי להתאים מודל חזק שהודרכה מראש למערך הנתונים שלנו.
הסדנה הזו כוללת את ההסברים התיאורטיים הנדרשים על רשתות נוירונים, והיא נקודת התחלה טובה למפתחים שמתחילים ללמוד על למידת עומק.
שיעור ה-Lab הזה הוא חלק 2 בסדרה "Keras on TPU". אפשר לעשות את זה בסדר הבא או בנפרד.
- צינורות עיבוד נתונים במהירות TPU: tf.data.Dataset ו-TFRecords
- [הסדנה הזו] המודל הראשון שלכם ב-Keras, עם למידת העברה
- רשתות נוירונים מלאכותיות (CNN), עם Keras ו-TPUs
- המרות מודרניות, דחיסה, Xception, עם Keras ומעבדי TPU
מה תלמדו
- כדי ליצור מסַווג תמונות משלך ב-Keras עם שכבת softmax ואובדן ב-Cross-entropy
- כדי לרמות 😈, אפשר להשתמש בלמידת העברה במקום ליצור מודלים משלכם.
משוב
אם תיתקלו בבעיה במעבדת הקוד הזו, נשמח לשמוע על כך. אפשר לשלוח משוב דרך 'בעיות ב-GitHub' [feedback link].
2. התחלה מהירה של Google Colaboratory
בשיעור ה-Lab הזה נעשה שימוש ב'שיתוף פעולה עם Google' ולא נדרשת הגדרה כלשהי מצדך. Colaboratory היא פלטפורמת notebook אונליין למטרות חינוכיות. באתר יש הדרכה בחינם בנושא מעבדים (CPU), מעבדי GPU ו-TPU.
אתם יכולים לפתוח את מסמך ה-notebook לדוגמה הזה ולעיין בכמה תאים כדי להכיר את Colaboratory.
בחירת קצה עורפי של TPU
בתפריט של Colab, בוחרים באפשרות Runtime > Change runtime type (סביבת זמן ריצה > שינוי הסוג של סביבת זמן הריצה) ואז בוחרים באפשרות TPU. בשיעור ה-Lab הזה תלמדו איך להשתמש ב-TPU (יחידת עיבוד טרנספורמציות טילר) חזקה עם תמיכה באימון שמואץ בחומרה. החיבור לסביבת זמן הריצה יתבצע באופן אוטומטי בהפעלה הראשונה, או שאפשר להשתמש בלחצן 'התחברות' בפינה השמאלית העליונה.
ביצוע של Notebook
כדי להפעיל תאים בכל פעם, לוחצים על תא באמצעות מקש Shift-ENTER. אפשר גם להריץ את כל ה-notebook באמצעות סביבת זמן הריצה > הרצת הכול
תוכן העניינים
בכל המחברות יש תוכן עניינים. אפשר לפתוח אותו באמצעות החץ השחור שמשמאל.
תאים מוסתרים
בחלק מהתאים תוצג רק הכותרת שלהם. זוהי תכונת notebook ספציפית ל-Colab. אפשר ללחוץ עליהם לחיצה כפולה כדי לראות את הקוד שבתוכם, אבל בדרך כלל הוא לא מעניין במיוחד. בדרך כלל תומכים בפונקציות או בפונקציות חזותיות. עדיין צריך להריץ את התאים האלה כדי שהפונקציות שבתוכם יוגדרו.
אימות
ל-Colab יש גישה לקטגוריות הפרטיות שלכם ב-Google Cloud Storage, בתנאי שתבצעו אימות באמצעות חשבון מורשה. קטע הקוד שלמעלה יפעיל תהליך אימות.
3. [INFO] מסווג רשת נוירונים 101
בקצרה
אם כל המונחים המודגשים בפסקה הבאה כבר מוכרים לכם, אפשר לעבור לתרגיל הבא. אם זו רק ההתחלה שלכם בלמידת עומק, ברוכים הבאים. כדאי להמשיך לקרוא.
עבור מודלים שנוצרו כרצף של שכבות, Keras מציעה את Sequential API. לדוגמה, אפשר לכתוב ב-Keras סיווג תמונות באמצעות שלוש שכבות צפופות כך:
model = tf.keras.Sequential([
tf.keras.layers.Flatten(input_shape=[192, 192, 3]),
tf.keras.layers.Dense(500, activation="relu"),
tf.keras.layers.Dense(50, activation="relu"),
tf.keras.layers.Dense(5, activation='softmax') # classifying into 5 classes
])
# this configures the training of the model. Keras calls it "compiling" the model.
model.compile(
optimizer='adam',
loss= 'categorical_crossentropy',
metrics=['accuracy']) # % of correct answers
# train the model
model.fit(dataset, ... )
רשת נוירונים צפופה
זוהי רשת העצבים הפשוטה ביותר לסיווג תמונות. הוא עשוי מ"נוירונים" שמסודרים בשכבות. השכבה הראשונה מעבדת את נתוני הקלט ומעבירה את הפלט שלה לשכבות אחרות. היא נקראת 'דחוס' כי כל נוירונים מחובר לכל נוירונים בשכבה הקודמת.
כדי להזין תמונה לרשת כזו, צריך לשטח את ערכי ה-RGB של כל הפיקסלים שלה וקטור ארוך ולהשתמש בו כקלט. זו לא הטכניקה הטובה ביותר לזיהוי תמונות, אבל נשתפר אותה בהמשך.
נוירונים, הפעלות, RELU
'נוירון' מחשב סכום משוקלל של כל הקלט שלו, מוסיף ערך שנקרא 'הטיה' ומעביר את התוצאה דרך 'פונקציית הפעלה'. המשקולות וההטיה לא ידועים בהתחלה. הם יופעלו באופן אקראי ו"ילמדו" על ידי אימון של רשת הנוירונים על כמות גדולה של נתונים ידועים.
פונקציית ההפעלה הפופולרית ביותר נקראת RELU עבור Rectified Linear Unit (יחידה לינארית מתוקנת). זוהי פונקציה פשוטה מאוד כפי שניתן לראות בתרשים שלמעלה.
הפעלה של Softmax
הרשת שלמעלה מסתיימת בשכבה של 5 נוירונים כי אנחנו מסווגים פרחים ל-5 קטגוריות (ורד, צבעוני, שן-ארי, חמנית, איריס). נוירונים בשכבות ביניים מופעלים באמצעות פונקציית ההפעלה הקלאסית של RELU. עם זאת, בשכבה האחרונה אנחנו רוצים לחשב מספרים בין 0 ל-1 שמייצגים את ההסתברות שהפרח הזה הוא ורד, צבעוני וכו'. לשם כך, נשתמש בפונקציית הפעלה שנקראת softmax.
כדי להחיל פונקציית softmax על וקטור, מחשבים את החזקה של כל רכיב ואז מבצעים נורמליזציה של הווקטור, בדרך כלל באמצעות נורמלי L1 (סכום הערכים המוחלטים) כך שהערכים יתווספו ל-1 וניתן יהיה לפרש אותם כprobabilities.
הפסד חוצה-אנטרופיה
עכשיו, כשרשת העצבים שלנו מייצרת תחזיות מתמונות קלט, אנחנו צריכים למדוד את מידת הדיוק שלהן, כלומר את המרחק בין מה שהרשת אומרת לנו לבין התשובות הנכונות, שנקראות לרוב 'תוויות'. חשוב לזכור שיש לנו תוויות נכונות לכל התמונות במערך הנתונים.
כל מרחק יכול להתאים, אבל במקרה של בעיות סיווג, "מרחק באנטרופיה חוצה" הוא היעיל ביותר. נתקשר לפונקציית השגיאה הזו או לפונקציית 'loss' (הפסדים):
ירידה בגרדינט
"אימון" של רשת הנוירונים פירושו שימוש בתמונות ובתוויות אימון כדי להתאים משקולות והטיות ולצמצם את פונקציית האיבוד החוצה-אנטרופיה. כך זה עובד.
ההסתברות הצולבת היא פונקציה של משקלים, הטיות, פיקסלים של תמונת האימון והכיתה הידועה שלה.
אם מחושבים הנגזרות הפרטיות של האנטרופיה הצולבת ביחס לכל המשקלים וכל הטיות, מתקבל 'שיפוע' שמחושב עבור תמונה, תווית וערך נוכחי נתונים של משקלים וטיות. חשוב לזכור שיכולים להיות לנו מיליוני משקלים ונטיות, ולכן חישוב השיפוע נשמע כמו הרבה עבודה. למרבה המזל, Tensorflow עושה את זה בשבילנו. התכונה המתמטית של שיפוע הוא שהוא מצביע "למעלה". מכיוון שאנחנו רוצים להגיע למיקום שבו ההסתברות הצולבת נמוכה, אנחנו הולכים בכיוון ההפוך. אנחנו מעדכנים את המשקל וההטיות לפי חלק מההדרגתיות. לאחר מכן אנחנו חוזרים על אותו תהליך שוב ושוב, באמצעות קבוצות התמונות והתוויות הבאות של אימון, בלולאת אימון. יש לקוות שהיא תגיע לנקודה שבה האנטרופיה ההצטלבותית תהיה מינימלית, אבל אין ערובה שהמינימום הזה יהיה ייחודי.
מיני-אצווה ומומנטום
ניתן לחשב את ההדרגתיות על תמונה אחת לדוגמה בלבד ולעדכן את המשקלים וההטיות באופן מיידי, אבל אם עושים זאת על קבוצה של, לדוגמה, 128 תמונות יוצר הדרגתי שמייצג טוב יותר את המגבלות שהוטלו על ידי תמונות לדוגמה שונות, ולכן סביר להניח שהן יתמזגו מהר יותר אל הפתרון. הגודל של קבוצת המשנה הוא פרמטר שניתן לשינוי.
לשיטה הזו, שנקראת לפעמים "ירידה הדרגתית סטוכסטית", יש יתרון נוסף, פרגמטי יותר: עבודה עם אצוות פירושה גם עבודה עם מטריצות גדולות יותר, ובדרך כלל קל יותר לבצע אופטימיזציה שלהן במעבדי GPU ובמעבדי TPU.
עם זאת, ההתכנסות עדיין יכולה להיות קצת כאוטית, ואפילו להיפסק אם וקטור המדרון כולל רק אפסים. האם המשמעות היא שמצאנו ערך מינימלי? לא תמיד. רכיב הדרגתי יכול להיות אפס במינימום או במקסימום. אם וקטור שיפוע מכיל מיליוני רכיבים, והם כולם אפס, הסבירות שכל אפס תואם לנקודת מינימום ואף אחת מהן לא תואמת לנקודת מקסימום היא קטנה למדי. במרחב עם הרבה מאפיינים, נקודות רכס הן נפוצות למדי, ואנחנו לא רוצים לעצור בהן.
איור: נקודת אוכף. שיפוע של 0, אבל הוא לא מינימום בכל הכיוונים. (קרדיט תמונה Wikimedia: By Nicoguaro - Own work, CC BY 3.0)
הפתרון הוא להוסיף קצת מומנטום לאלגוריתם האופטימיזציה כדי שיוכל לעבור נקודות רכס בלי לעצור.
מילון מונחים
batch או mini-batch: תמיד מתבצע אימון על קבוצות של נתוני אימון ותוויתות. כך אפשר לעזור לאלגוריתם להגיע להסכמה. המאפיין 'אצווה' הוא בדרך כלל המימד הראשון של מזנוני הנתונים. לדוגמה, Tensor של צורה [100, 192, 192, 3] מכיל 100 תמונות של 192x192 פיקסלים עם שלושה ערכים לכל פיקסל (RGB).
אובדן אנטרופי חוצה: פונקציית אובדן מיוחדת שמשמשת לרוב בסווגים.
שכבה צפופה: שכבה של נוירונים שבה כל נוירונים מחובר לכל נוירונים בשכבה הקודמת.
מאפיינים: הקלט של רשת נוירונים נקרא לפעמים 'מאפיינים'. האמנות של זיהוי החלקים בקבוצת נתונים (או שילובים של חלקים) שצריך להזין לרשת נוירונים כדי לקבל תחזיות טובות נקראת 'פיתוח מאפיינים'.
labels: שם נוסף ל'כיתות' או לתשובות נכונות בבעיה של סיווג בפיקוח
שיעור הלמידה: חלק מהמדריגנט שבו משקולות ונטיות מועדכנים בכל חזרה של לולאת האימון.
logits: הפלט של שכבת תאי עצב לפני החלת פונקציית ההפעלה נקרא 'logits'. המונח נגזר מ'פונקציה לוגיסטית', שנקראת גם 'פונקציית סיגמואיד', שהייתה בעבר פונקציית ההפעלה הפופולרית ביותר. 'פלט נוירונים לפני פונקציה לוגיסטי' קוצר ל-'logits'.
loss (הפסד): פונקציית השגיאה שמשווה בין פלטי רשת נוירונים לתשובות הנכונות
נוירון: מחשב את הסכום המשוקלל של הקלט שלו, מוסיף הטיה ומעביר את התוצאה דרך פונקציית הפעלה.
קידוד one-hot: הכיתה 3 מתוך 5 מקודדת כוקטור של 5 רכיבים, כולם אפס מלבד הרכיב השלישי שהוא 1.
relu: יחידה לינארית מתוקנת. פונקציית הפעלה פופולרית לנוירונים.
sigmoid: פונקציית הפעלה נוספת שבעבר הייתה פופולרית ועדיין שימושית במקרים מיוחדים.
softmax: פונקציית הפעלה מיוחדת שפועלת על וקטור, מגדילה את ההפרש בין הרכיב הגדול ביותר לבין כל האחרים, וגם מנרמלת את הווקטור לסכום של 1 כדי שאפשר יהיה לפרש אותו כווקטור של הסתברויות. משמש כשלב האחרון במסווגים.
tensor: 'tensor' הוא כמו מטריצה, אבל עם מספר שרירותי של מאפיינים. טינסור בעל מימד אחד הוא וקטור. טינסור דו-מימדי הוא מטריצת. לאחר מכן אפשר ליצור טינסורים עם 3, 4, 5 או יותר מאפיינים.
4. למידת העברה
בבעיה של סיווג תמונות, שכבות צפופות לא יספיקו. עלינו ללמוד על שכבות קונבולוציה ועל הדרכים הרבות שבהן ניתן לארגן אותן.
אבל אפשר גם לקצר את התהליך. יש רשתות נוירונים קונבולוציה שאומנו באופן מלא וזמינות להורדה. אפשר לחתוך את השכבה האחרונה שלהם, 'ראש הסיווג של softmax', ולהחליף אותה בשכבה משלכם. כל המשקלים וההטיות שהותאמו נשארים כפי שהם, ומתאימים מחדש רק את שכבת ה-softmax שמוסיפים. השיטה הזו נקראת 'למידת העברה' ומדהימה, היא פועלת כל עוד מערך הנתונים שעליו רשת הנוירונים אומנו מראש "קרוב מספיק" לשלכם.
שיחה קולית
עליך לפתוח את ה-notebook הבא, להריץ את התאים (Shift-ENTER) ולפעול לפי ההוראות בכל מקום שבו מופיעה התווית 'נדרשת עבודה'.
Keras Flowers transfer learning (playground).ipynb
מידע נוסף
למידה של ההעברה מאפשרת לכם להפיק תועלת מארכיטקטורות מתקדמות של רשתות נוירונים מלאכותיות שפותחו על ידי חוקרים מובילים, וגם מאימון מראש של מערך נתונים עצום של תמונות. במקרה שלנו, נבצע העברת למידת רשת מרשת שהודרכה ב-ImageNet, מסד נתונים של תמונות שמכיל הרבה צמחים וסצינות חוץ, שדומה למדי לפרחים.
איור: שימוש ברשת נוירונים קוונטית מורכבת שכבר הוכשרה, כקופסה שחורה, והכשרה מחדש של 'ראש' הסיווג בלבד. זאת למידת העברה. בהמשך נראה איך פועלים הסדרים המורכבים האלה של השכבות המסתלות. בינתיים, זו בעיה של מישהו אחר.
למידה שהועברה ב-Keras
ב-Keras, אפשר ליצור מודל שעבר אימון מראש מהאוסף tf.keras.applications.*
. לדוגמה, MobileNet V2 היא ארכיטקטורה נוירונלית טובה מאוד עם גודל סביר. אם בוחרים באפשרות include_top=False
, מקבלים את המודל שעבר אימון מראש בלי שכבת ה-softmax הסופית שלו, ואז אפשר להוסיף לו:
pretrained_model = tf.keras.applications.MobileNetV2(input_shape=[*IMAGE_SIZE, 3], include_top=False)
pretrained_model.trainable = False
model = tf.keras.Sequential([
pretrained_model,
tf.keras.layers.Flatten(),
tf.keras.layers.Dense(5, activation='softmax')
])
שימו לב גם להגדרה pretrained_model.trainable = False
. המודל מקפיא את המשקולות ואת ההטיות של המודל שעבר אימון מראש, כדי לאמן את שכבת ה-softmax בלבד. בדרך כלל התהליך הזה כולל מעט משקולות ואפשר לבצע אותו במהירות ובלי צורך במערך נתונים גדול מאוד. עם זאת, אם יש לכם הרבה נתונים, תוכלו לשפר את הלמידה של ההעברה באמצעות pretrained_model.trainable = True
. לאחר מכן, המשקלים שהותאמו מראש מספקים ערכים ראשוניים מצוינים, ועדיין אפשר לשנות אותם במהלך האימון כדי להתאים אותם טוב יותר לבעיה.
לבסוף, שימו לב לשכבה Flatten()
שמוחדרת לפני שכבת ה-softmax הצפופה. שכבות צפופות פועלות על וקטורים שטוחים של נתונים, אבל אנחנו לא יודעים אם זה מה שהמודל המאומן מראש מחזיר. בגלל זה אנחנו צריכים ליישר קו. בפרק הבא, אחרי שנתעמק בארכיטקטורות קונבולוציה, נסביר את פורמט הנתונים שהוחזר על ידי שכבות קונבולוציה.
הגישה הזו אמורה לספק דיוק של כ-75%.
פתרון
הנה ה-notebook של הפתרון. אפשר להשתמש בו אם נתקעתם.
Keras Flowers transfer learning (solution).ipynb
אילו נושאים דיברנו?
- 🤔 איך כותבים סיווג ב-Keras
- 🤓 שהוגדרו עם שכבה אחרונה של softmax, ואובדן ב-Cross-entropy
- 😈 להעביר את הלמידה
- 🤔 אימון המודל הראשון
- 🧐 בעקבות ההפסד והדיוק שלהן במהלך האימון
כדאי להקדיש כמה רגעים כדי לעבור על רשימת המשימות הבאה בראש שקט.
5. מעולה!
עכשיו אפשר ליצור מודל Keras. בשיעור ה-Lab הבא תלמדו איך להרכיב שכבות עיבוד קוונטי.
- צינורות עיבוד נתונים במהירות TPU: tf.data.Dataset ו-TFRecords
- [THIS LAB] מודל Keras הראשון שלכם, עם למידת העברה
- רשתות נוירונים מלאכותיות (CNN), עם Keras ו-TPUs
- המרות מודרניות, דחיסה, Xception, עם Keras ומעבדי TPU
מעבדי TPU בפועל
מעבדי TPU ו-GPU זמינים ב-Cloud AI Platform:
- במכונות וירטואליות ללמידה עמוקה (Deep Learning)
- ב-notebooks של AI Platform
- במשימות של AI Platform Training
לסיום, אנחנו אוהבים לקבל משוב. נשמח לדעת אם משהו השתבש בשיעור ה-Lab הזה או אם לדעתכם צריך לשפר אותו. אפשר לשלוח משוב דרך בעיות ב-GitHub [קישור למשוב].
|