none
האם ניתן לגשת לאובייקט "לא קיים"? RRS feed

  • שאלה

  • שלום לכולם,

    לאחרונה אני מתחזק ומשפר מעט את כישורי ה-c# שלי, שלא היו גבוהים מלכתחילה.

    אני זוכר שתמיד הייתי נניח רוצה לבדוק האם אובייקט ריק או לא הייתי עושה If פשוט:

    if(myObject!=null)

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

    כמו לדוגמא זה:

                string b;
                Console.WriteLine(b.GetType());

    או לדוגמא:

                string b ="";
                Console.WriteLine(b[0].GetType());

    אני יודע שזה ברור מאליו שזה אמור לא לפעות כי אני מנסה כביכול לגשת לאיברים לא קיימים אבל אני זוכר שתמיד עבדתי כך:\

    תודה רבה!

    מיקי

    יום רביעי 12 פברואר 2014 22:22

תשובות

  • אהלן מיקי,

    מה שאתה זוכר מגיע כניראה ממשפחת שפות בייסיק כמו למשל VBS או VB.Net ולא מ C# :-)
    או ממקרה שונה מעט כמו בעבודה עם אוספים או מסדי נתונים ובכלל.

    צריך להפריד בין מצב בו אלמנט לא קיים בכלל לבין מצב בו האלמנט ריק. למשל 

    // האלמנט לא קיים בכלל
    Class1 myVar1;
    // האלמנט קים אבל הוא ריק
    Class1 myVar2 = null;

    המקרה הראשון אם תנסה להישתמש באלמנט אז הקומפיילר של C# כבר יעצור את ההתקדמות (כפי שכתב Bresleveloper). אבל במקרה השני תוכל לבצע בדיקות כמו בדיקת התנאי myVar2 == null

    בשימוש ב VB.Net לעומת זאת אפשר לעבוד גם עם אלמנטים לא מוגדרים בעזרת המתודה IsDBNull למשל הקוד הבא יעבוד טוב:

            Dim _S As String
    
            If IsDBNull(_S) Then
                Console.WriteLine("YES")
            Else
                Console.WriteLine("NO")
            End If

    אין לזה משהו מקביל לחלוטין ב C# אם כי יש מתודה דומה תחת CONVERT, אבל השימוש שונה.

    ישנם כל מני בדיקות שיכולות לעזור בדומה ל myVar2 == null כמו למשל שימוש ב object.Equals אבל בדיקות אלו לא נועדו לזיהוי מצב של  object reference not set to an instance of an object וזה המקרה שאתה מציג.

    * יש הבדל אם אתה עובד עם reference type או עם value type וישנם עוד כמה נקודות שצריך לחשוב בכל מקרה, אבל כאמור אין מקבילה מלאה לפעולה שיש ב VB. בעקרון זה באחריות המפתח לא להגיע למצב כזה (והקומפיילר יעזור לך בכך).


    [Personal Site] [Blog] [Facebook]signature

    • נערך על-ידי pituachMVP, Moderator יום חמישי 13 פברואר 2014 10:59
    • סומן כתשובה על-ידי Juda Michael יום חמישי 13 פברואר 2014 11:02
    יום חמישי 13 פברואר 2014 10:56
    מנחה דיון

כל התגובות

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

    שים קוד מלא לבעיה המלאה

    יום חמישי 13 פברואר 2014 10:38
  • אהלן מיקי,

    מה שאתה זוכר מגיע כניראה ממשפחת שפות בייסיק כמו למשל VBS או VB.Net ולא מ C# :-)
    או ממקרה שונה מעט כמו בעבודה עם אוספים או מסדי נתונים ובכלל.

    צריך להפריד בין מצב בו אלמנט לא קיים בכלל לבין מצב בו האלמנט ריק. למשל 

    // האלמנט לא קיים בכלל
    Class1 myVar1;
    // האלמנט קים אבל הוא ריק
    Class1 myVar2 = null;

    המקרה הראשון אם תנסה להישתמש באלמנט אז הקומפיילר של C# כבר יעצור את ההתקדמות (כפי שכתב Bresleveloper). אבל במקרה השני תוכל לבצע בדיקות כמו בדיקת התנאי myVar2 == null

    בשימוש ב VB.Net לעומת זאת אפשר לעבוד גם עם אלמנטים לא מוגדרים בעזרת המתודה IsDBNull למשל הקוד הבא יעבוד טוב:

            Dim _S As String
    
            If IsDBNull(_S) Then
                Console.WriteLine("YES")
            Else
                Console.WriteLine("NO")
            End If

    אין לזה משהו מקביל לחלוטין ב C# אם כי יש מתודה דומה תחת CONVERT, אבל השימוש שונה.

    ישנם כל מני בדיקות שיכולות לעזור בדומה ל myVar2 == null כמו למשל שימוש ב object.Equals אבל בדיקות אלו לא נועדו לזיהוי מצב של  object reference not set to an instance of an object וזה המקרה שאתה מציג.

    * יש הבדל אם אתה עובד עם reference type או עם value type וישנם עוד כמה נקודות שצריך לחשוב בכל מקרה, אבל כאמור אין מקבילה מלאה לפעולה שיש ב VB. בעקרון זה באחריות המפתח לא להגיע למצב כזה (והקומפיילר יעזור לך בכך).


    [Personal Site] [Blog] [Facebook]signature

    • נערך על-ידי pituachMVP, Moderator יום חמישי 13 פברואר 2014 10:59
    • סומן כתשובה על-ידי Juda Michael יום חמישי 13 פברואר 2014 11:02
    יום חמישי 13 פברואר 2014 10:56
    מנחה דיון
  • כלומר שאני חייב לאתחל את המשתנים. למרות שחשבתי שהם מקבלים ערכי ברירת מחדל אוטמאטיים.

    הבנתי.

    תודה רבה לשניכם!!

    יום חמישי 13 פברואר 2014 11:03