שגיאת האוסף "לא מוצא סמל"

1. סקירה כללית

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

2. הידור שגיאות זמן

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

בעיקרון, ישנם שלושה סוגים של שגיאות זמן הידור:

  • יכולות להיות לנו שגיאות תחביר. אחת הטעויות הנפוצות ביותר שכל מתכנת יכול לעשות היא לשכוח לשים את נקודה-פסיק בסוף ההצהרה; חלק אחר שוכח יבוא, סוגריים לא מתאימים או השמטת הצהרת ההחזר
  • הבא, יששגיאות בדיקת סוג. זהו תהליך של אימות בטיחות סוג בקוד שלנו. בבדיקה זו אנו מוודאים שיש לנו סוגים עקביים של ביטויים. לדוגמא, אם אנו מגדירים משתנה מסוג int, לעולם לא נקצה א לְהַכפִּיל אוֹ חוּט ערך לזה
  • בינתיים, קיימת אפשרות שהמהדר יתרסק. זה נדיר מאוד אבל זה יכול לקרות. במקרה זה, טוב לדעת שהקוד שלנו אולי לא מהווה בעיה, אלא שמדובר בבעיה חיצונית

3. השגיאה "לא מוצא סמל"

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

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

3.1. מה יכול לגרום "לא מוצא סמל" שְׁגִיאָה?

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

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

קוד המקור של Java שלנו מורכב מ:

  • מילות מפתח: נכון, שקר, מעמד, בעוד
  • מילות: מספרים וטקסט
  • מפעילים ואסימונים אחרים שאינם אלפאנומריים: -, /, +, =, {
  • מזהים: רָאשִׁי, קוֹרֵא, אני, toString, וכו.
  • הערות ומרחב לבן

4. שגיאות כתיב

הנושאים הנפוצים ביותר קשורים לאיות. אם נזכור שכל מזהי Java הם תלויי רישיות, אנו יכולים לראות כי:

  • StringBiulder
  • stringBuilder
  • String_Builder

כל אלה היו דרכים שונות להתייחס באופן שגוי ל StringBuilder מעמד.

5. היקף מופע

שגיאה זו יכולה להיגרם גם כאשר משתמשים במשהו שהוכרז מחוץ לתחום הכיתה.

לדוגמא, נניח שיש לנו מאמר כיתה שקוראת a createId שיטה:

מאמר בכיתה ציבורית {אורך פרטי פרטי; מזהה פרטי פרטי; מאמר ציבורי (אורך int) {this.length = אורך; this.id = createId (); }}

אבל, אנו מכריזים על createId שיטה בכיתה נפרדת:

מחלקה ציבורית IdGenerator {public long generId () {אקראי אקראי = אקראי חדש (); החזר random.nextInt (); }}

עם הגדרה זו, המהדר ייתן שגיאת "לא יכול למצוא סמל" עבור createId על קו 7 של מאמר קטע. הסיבה היא שהתחביר של שורה 7 מרמז כי ה- createId שיטה מוכרז ב מאמר.

כמו בכל השפות הבוגרות, יש יותר מדרך אחת לטפל בנושא זה. אבל, דרך אחת תהיה לבנות IdGenerator בתוך ה מאמר ואז לקרוא לשיטה:

מאמר בכיתה ציבורית {אורך פרטי פרטי; מזהה פרטי פרטי; מאמר ציבורי (אורך int) {this.length = אורך; this.id = IdGenerator חדש (). generateId (); }}

6. משתנים לא מוגדרים

לפעמים אנו שוכחים להכריז על המשתנה. כפי שניתן לראות מהקטע הבא, אנו מנסים לתפעל את המשתנה שלא הכרזנו, במקרה זה, טֶקסט:

מאמר בכיתה ציבורית {אורך פרטי פרטי; // ... set public setText (String newText) {this.text = newText; // מעולם לא הוגדר משתנה טקסט}}

אנו פותרים בעיה זו על ידי הכרזת המשתנה טֶקסט מהסוג חוּט:

מאמר בכיתה ציבורית {אורך פרטי פרטי; טקסט מחרוזת פרטי; // ... set public setText (String newText) {this.text = newText; }}

7. היקף משתנה

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

משתנים בתוך הלולאה אינם נגישים מחוץ לולאה:

findLetterB ציבורי בוליאני (טקסט מחרוזת) {for (int i = 0; i <text.length (); i ++) {Character character = text.charAt (i); אם (String.valueOf (character) .equals ("b")) {return true; } להחזיר שקר; } אם (תו == "a") {// <- שגיאה! ...}}

ה אם ההצהרה צריכה להיכנס לתוכנה לולאה אם עלינו לבחון דמויות נוספות:

findLetterB ציבורי בוליאני (טקסט מחרוזת) {for (int i = 0; i <text.length (); i ++) {Character character = text.charAt (i); אם (String.valueOf (character) .equals ("b")) {return true; } אחרת אם (String.valueOf (character) .equals ("a")) {...} return false; }}

8. שימוש לא חוקי בשיטות או בשדות

השגיאה "לא יכול למצוא סמל" תתרחש גם אם אנו משתמשים בשדה כשיטה או להיפך:

מאמר בכיתה ציבורית {אורך פרטי פרטי; מזהה פרטי פרטי; טקסטים פרטיים של רשימה; מאמר ציבורי (אורך int) {this.length = אורך; } // גטרים וקובעים}

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

מאמר מאמר = מאמר חדש (300); טקסטים ברשימה = article.texts ();

ואז היינו רואים את השגיאה.

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

למעשה, יש גטר שיטה בה אנו יכולים להשתמש במקום:

מאמר מאמר = מאמר חדש (300); טקסטים ברשימה = article.getTexts ();

פעולה שגויה על מערך ולא על אלמנט מערך היא גם בעיה:

עבור (טקסט מחרוזת: טקסטים) {String firstLetter = texts.charAt (0); // זה צריך להיות text.charAt (0)}

וכך גם לשכוח את חָדָשׁ מילת מפתח כמו ב:

מחרוזת s = מחרוזת (); // צריך להיות 'מחרוזת חדשה ()'

9. יבוא חבילה ושיעורים

בעיה נוספת היא שכחה לייבא את המחלקה או החבילה. לדוגמא, שימוש ב- רשימה אובייקט מבלי לייבא java.util.List:

// חסר הצהרת ייבוא: // ייבא java.util.List סוג ציבורי מאמר {אורך פרטי פרטי; מזהה פרטי פרטי; טקסטים פרטיים של רשימה; שגיאה! מאמר ציבורי (אורך int) {this.length = אורך; }}

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

10. יבוא לא נכון

ייבוא ​​סוג שגוי, בשל השלמת IDE או תיקון אוטומטי הוא גם נושא נפוץ.

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

תאריך תאריך = תאריך חדש (); שנה int, חודש, יום;

כדי לקבל את השנה, החודש או היום עבור java.util.Date, אנחנו גם צריכים לייבא לוּחַ שָׁנָה לחלק ולחלץ משם את המידע.

פשוט קורא השג תאריך() מ java.util.Date לא יעבוד:

... date.getDay (); date.getMonth (); date.getYear ();

במקום זאת, אנו משתמשים ב- לוּחַ שָׁנָה לְהִתְנַגֵד:

... לוח שנה cal = Calendar.getInstance (TimeZone.getTimeZone ("אירופה / פריז")); cal.setTime (תאריך); שנה = cal.get (Calendar.YEAR); חודש = cal.get (Calendar.MONTH); יום = cal.get (לוח שנה. DAY_OF_MONTH);

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

... LocalDate localDate = date.toInstant (). AtZone (ZoneId.systemDefault ()). ToLocalDate (); שנה = localDate.getYear (); חודש = localDate.getMonthValue (); יום = localDate.getDayOfMonth ();

11. מסקנה

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

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