זוהי אחת מיני סדרות שמכסה את ההבדלים בעומס יתר, צללים ועקיפה VB.NET. מאמר זה מכסה עקיפות. המאמרים המכסים את האחרים כאן:
-> עומסי יתר
-> צללים
טכניקות אלה יכול להיות מבלבל מאוד; ישנם המון שילובים של מילות מפתח אלה ואפשרויות הירושה הבסיסיות. התיעוד של מיקרוסופט עצמה לא מתחיל לעשות את הנושא בצדק ויש הרבה מידע רע או לא מעודכן באינטרנט. העצה הטובה ביותר לוודא שהתוכנה שלך מקודדת כהלכה היא "בדוק, בדוק ובדוק שוב." בסדרה זו, נסתכל עליהם בזה אחר זה עם דגש על ההבדלים.
עוקף
הדבר המשותף לכולם בין צללים, עומס יתר ועקיפה הוא שהם משתמשים מחדש בשם האלמנטים תוך שינוי מה שקורה. צללים ועומסי יתר יכולים לפעול שניהם באותה מעמד או כאשר א הכיתה יורשת כיתה אחרת. עם זאת, ניתן להשתמש בהפרסות רק בכיתה נגזרת (המכונה לעיתים כיתת ילדים) שירושה מ- א מחלקת בסיס (נקרא לפעמים כיתת הורים). ועקיפה היא הפטיש; זה מאפשר לך להחליף לחלוטין שיטה (או נכס) ממחלקת בסיס.
במאמר על שיעורים ומילת המפתח צללים (ראה: צללים ב- VB.NET), נוספה פונקציה כדי להראות שאפשר להפנות לתהליך בירושה.
איש קשר בכיתה ציבורית. '... הקוד לא מוצג... פונקציה ציבורית HashTheName ( ByVal nm כמו מחרוזת) כמחרוזת. חזור nm. GetHashCode. פונקצית סיום. סיום כיתה.
הקוד המיישם מחלקה הנגזרת מקודד זה (CodedProfessionalContact בדוגמה) יכול לקרוא לשיטה זו מכיוון שהיא עוברת בירושה.
בדוגמה השתמשתי ב- VB.NET GetHashCode שיטה כדי לשמור על קוד פשוט וזה החזיר תוצאה חסרת תועלת למדי, ערך -520086483. נניח שרציתי שתוצאה אחרת תחזור במקום, אבל,
-> אני לא יכול לשנות את מחלקת הבסיס. (אולי כל מה שיש לי הוא קובץ קוד מאת ספק.)
... ו ...
-> אני לא יכול לשנות את קוד השיחה (אולי יש אלף עותקים ואני לא יכול לעדכן אותם.)
אם אוכל לעדכן את הכיתה הנגזרת, אוכל לשנות את התוצאה שהוחזרה. (לדוגמה, הקוד יכול להיות חלק מ- DLL שניתן לעדכון.)
יש בעיה אחת. מכיוון שזה כל כך מקיף ועוצמתי, אתה צריך לקבל אישור מכיתת הבסיס להשתמש ב- Overrides. אבל ספריות קוד מעוצבות מספקות את זה. (שלך ספריות קוד כולן מעוצבות היטב, נכון?) לדוגמה, הפונקציה המסופקת של מיקרוסופט שהשתמשנו זה עתה ניתנת להחלפה. להלן דוגמא לתחביר.
פונקציה ציבורית הניתנת להחלפה GetHashCode כמספר שלם
כך שמילת המפתח צריכה להיות קיימת גם במחלקת הבסיס לדוגמה.
הפונקציה הניתנת להחלפה ציבורית HashTheName ( ByVal nm כמו מחרוזת) כמחרוזת.
גובר על השיטה זה עכשיו פשוט כמו לספק אחד חדש עם מילת המפתח Overrides. Visual Studio שוב נותן לך התחלה ריצה על ידי מילוי הקוד עבורך באמצעות השלמה אוטומטית. כשאתה נכנס ...
פונקציה עוקפת ציבורית HashTheName (
Visual Studio מוסיף את שאר הקוד באופן אוטומטי ברגע שאתה מקליד את הסוגריים הפותחים, כולל הצהרת החזרה שקוראת רק לפונקציה המקורית ממחלקת הבסיס. (אם אתה רק מוסיף משהו, בדרך כלל זה דבר טוב לעשות לאחר שהקוד החדש שלך יופיע בכל מקרה.)
פונקציה עוקפת ציבורית HashTheName ( nm כמו מחרוזת) כמו מחרוזת. החזר את MyBase. HashTheName (nm) פונקצית סיום.
עם זאת, במקרה זה, אני הולך להחליף את השיטה במשהו אחר חסר תועלת באותה מידה רק כדי להמחיש כיצד היא נעשית: פונקציית VB.NET שתהפוך את המחרוזת.
פונקציה עוקפת ציבורית HashTheName ( nm כמו מחרוזת) כמו מחרוזת. החזיר את מיקרוסופט. ויז'ואל בייסיק. StrReverse (nm) פונקצית סיום.
כעת קוד השיחה מקבל תוצאה שונה לחלוטין. (השווה עם התוצאה במאמר על צללים.)
איש קשר: 246. שם עסקי: Villain Defeaters, GmbH. Hash of the BusinessName: HbmG, sretaefeD nialliV.
ניתן לעקוף גם מאפיינים. נניח שהחלטת שערכי ContactID הגדולים מ- 123 לא יאפשרו וכי ברירת המחדל היא 111. אתה יכול פשוט לעקוף את הנכס ולשנות אותו כאשר הנכס נשמר:
פרטי _ContactID כמספר שלם. גובר על הציבור קשר עם רכוש כמספר שלם. לקבל. החזר _ContactID. סוף גט. הגדר (ערך ByVal כמספר שלם) אם ערך> 123 ואז. _ContactID = 111. אחרת. _ContactID = ערך. סוף אם. סיום סט. נכס קצה.
ואז תקבל תוצאה זו כאשר מועבר ערך גדול יותר:
איש קשר: 111. שם עסקי: מצילי Damsel, בע"מ.
אגב, בקוד הדוגמא עד כה, ערכים שלמים מוכפלים ב- New תת-רוטינה (עיין במאמר על צללים), כך מספר שלם של 123 משתנה ל 246 ואז שוב משתנה ל 111.
VB.NET מעניק לך, אפילו יותר, שליטה בכך שהיא מאפשרת למחלקת בסיס לדרוש או לשלול באופן ספציפי מחלקה נגזרת לעקוף באמצעות מילות המפתח MustOverride ו- NotOverridable במחלקת הבסיס. אך בשני אלה משתמשים במקרים ספציפיים למדי. ראשית, לא ניתן להפעלה.
מכיוון שברירת המחדל לשיעור ציבורי אינה ניתנת להפעלה, מדוע אי פעם תצטרך לציין אותה? אם אתה מנסה את זה בפונקציה HashTheName במחלקת הבסיס, תקבל שגיאת תחביר, אך טקסט הודעת השגיאה נותן לך מושג:
לא ניתן להגדיר 'NotOverridable' עבור שיטות שאינן מבטלות שיטה אחרת.
ברירת המחדל לשיטה שגורסת היא הפוכה: ניתן להחלפה. אז אם ברצונכם שהאוניברסיטה תפסיק שם, עליכם לציין את NotOverridable בשיטה זו. בקוד הדוגמה שלנו:
לא ניתן לציין ציבורי עוקף פונקציה HashTheName (...
ואז אם הכיתה CodedProfessionalContact הוא, בתורו, בירושה ...
NotOverridableEx בכיתה ציבורית. יורש CodedProfessional Contact.
... לא ניתן לבטל את הפונקציה HashTheName באותה כיתה. אלמנט שלא ניתן לעקוף אותו נקרא לעיתים אלמנט אטום.
חלק מהותי מ- ה .קרן NET היא לדרוש כי מטרת כל כיתה מוגדרת במפורש להסרת כל חוסר הוודאות. בעיה בשפות OOP קודמות נקראה "מעמד הבסיס השברירי." זה קורה כאשר בסיס class מוסיף שיטה חדשה עם אותו שם כמו שם שיטה בתת-משנה שירושה מבסיס מעמד. המתכנת שכתב את תת המשנה לא התכוון לעקוף את מעמד הבסיס, אבל זה בדיוק מה שקורה בכל מקרה. ידוע שזה גורם לזעקתו של המתכנת הפצוע, "לא שיניתי שום דבר, אבל התוכנית שלי קרסה בכל מקרה. "אם קיימת אפשרות שכיתה תתעדכן בעתיד ותיצור את הבעיה הזו, הכרז עליה כ- לא ניתן להחלפה.
MustOverride משמש לרוב במה שמכונה כיתת מופשט. (ב- C #, אותו דבר משתמש במילת המפתח תקציר!) זו כיתה שרק מספקת תבנית וצפוי למלא אותה בקוד משלך. מיקרוסופט מספקת דוגמה זו לאחת:
מכונות כביסה בכלי ציבור שחייבים לעבור בירושה. תת חדש () קוד להפעלת הכיתה הולך לכאן. סוף תת. רחצה תת-רחצה MustOverride ציבורית. שטיפה תת רחבה ציבורית חייבת (loadSize כמספר שלם) סיבוב פונקציות MustOverride ציבורי (מהירות כמספר שלם) כארוך. סיום כיתה.
כדי להמשיך בדוגמה של מיקרוסופט, מכונות כביסה יעשו את הדברים האלה (שטיפה, שטיפה וספין) בצורה שונה לגמרי, כך שאין יתרון בהגדרת הפונקציה במחלקת הבסיס. אבל יש יתרון בכך שתוודא שכל מעמד שירש את המעמד הזה עושה הגדירו אותם. הפיתרון: שיעור מופשט.
אם אתה זקוק להסבר רב עוד יותר על ההבדלים בין עומסי יתר לבין עקיפות, דוגמה שונה לחלוטין מפותחת בטיפ מהיר: עומס יתר לעומת עקיפות יתר
VB.NET מעניקה לך שליטה רבה יותר על ידי כך שהיא מאפשרת למחלקת בסיס לדרוש או לשלול באופן ספציפי את הכיתה הנגזרת לבטל באמצעות מילות המפתח MustOverride ו- NotOverridable במחלקת הבסיס. אך בשני אלה משתמשים במקרים ספציפיים למדי. ראשית, לא ניתן להפעלה.
מכיוון שברירת המחדל לשיעור ציבורי אינה ניתנת להפעלה, מדוע אי פעם תצטרך לציין אותה? אם אתה מנסה את זה בפונקציה HashTheName במחלקת הבסיס, תקבל שגיאת תחביר, אך טקסט הודעת השגיאה נותן לך מושג:
לא ניתן להגדיר 'NotOverridable' עבור שיטות שאינן מבטלות שיטה אחרת.
ברירת המחדל לשיטה שגורסת היא הפוכה: ניתן להחלפה. אז אם ברצונכם שהאוניברסיטה תפסיק שם, עליכם לציין את NotOverridable בשיטה זו. בקוד הדוגמה שלנו:
לא ניתן לציין ציבורי עוקף פונקציה HashTheName (...
ואז אם הכיתה CodedProfessionalContact הוא, בתורו, בירושה ...
NotOverridableEx בכיתה ציבורית. יורש CodedProfessional Contact.
... לא ניתן לבטל את הפונקציה HashTheName באותה כיתה. אלמנט שלא ניתן לעקוף אותו נקרא לעיתים אלמנט אטום.
חלק מהותי של קרן .NET הוא לדרוש כי המטרה של כל כיתה מוגדרת במפורש להסרת כל חוסר הוודאות. בעיה בשפות OOP קודמות נקראה "מעמד הבסיס השברירי." זה קורה כאשר בסיס class מוסיף שיטה חדשה עם אותו שם כמו שם שיטה בתת-משנה שירושה מבסיס מעמד. המתכנת שכתב את תת המשנה לא התכוון לעקוף את מעמד הבסיס, אבל זה בדיוק מה שקורה בכל מקרה. ידוע שזה גורם לזעקתו של המתכנת הפצוע, "לא שיניתי שום דבר, אבל התוכנית שלי קרסה בכל מקרה. "אם קיימת אפשרות שכיתה תתעדכן בעתיד ותיצור את הבעיה הזו, הכרז עליה כ- לא ניתן להחלפה.
MustOverride משמש לרוב במה שמכונה כיתת מופשט. (ב- C #, אותו דבר משתמש במילת המפתח תקציר!) זו כיתה שרק מספקת תבנית וצפוי למלא אותה בקוד משלך. מיקרוסופט מספקת דוגמה זו לאחת:
מכונות כביסה בכלי ציבור שחייבים לעבור בירושה. תת חדש () קוד להפעלת הכיתה הולך לכאן. סוף תת. רחצה תת-רחצה MustOverride ציבורית. שטיפה תת רחבה ציבורית חייבת (loadSize כמספר שלם) סיבוב פונקציות MustOverride ציבורי (מהירות כמספר שלם) כארוך. סיום כיתה.
כדי להמשיך בדוגמה של מיקרוסופט, מכונות כביסה יעשו את הדברים האלה (שטיפה, שטיפה וספין) בצורה שונה לגמרי, כך שאין יתרון בהגדרת הפונקציה במחלקת הבסיס. אבל יש יתרון בכך שתוודא שכל מעמד שירש את המעמד הזה עושה הגדירו אותם. הפיתרון: שיעור מופשט.
אם אתה זקוק להסבר רב עוד יותר על ההבדלים בין עומסי יתר לבין עקיפות, דוגמה שונה לחלוטין מפותחת בטיפ מהיר: עומס יתר לעומת עקיפות יתר