מה זו שגיאה לוגית (Logic Error)?
שגיאה לוגית (logic error) היא טעות בהיגיון של תוכנית, שגורמת לה להפיק תוצאה שגויה בלי לקרוס ובלי להציג שום הודעת שגיאה. הקוד תקין וכל שורה רצה, אבל הוא לא עושה את מה שהמתכנת התכוון שיעשה.
עודכן ב-24 בספטמבר 2026
לשלושה ציוני מבחן, 80, 90 ו-100, יש ממוצע של 90. התוכנית הזו רצה בלי שום תלונה ומדפיסה משהו אחר:
Average: 203.33333333333334
Python עשתה בדיוק את מה שהשורה אומרת. חילוק קורה לפני חיבור, ולכן רק הציון האחרון חולק ב-3, והתוצאה היא 80 + 90 + 33.33. המתכנת התכוון ל-(scores[0] + scores[1] + scores[2]) / 3. הוסיפו את הסוגריים והתוכנית מדפיסה Average: 90.0.
למה לא מופיעה הודעת שגיאה
המחשב בודק אם קוד תקין, לא אם הוא נכון. ה-parser בודק את הדקדוק, וכך נתפסת שגיאת תחביר. סביבת הריצה בודקת כל פעולה, וכך נתפסת שגיאת זמן ריצה כמו חלוקה באפס. חיבור של שלושה מספרים וחילוק של אחד מהם ב-3 הוא דקדוק תקין ופעולה חוקית, ולכן שתי הבדיקות עוברות.
רק מי שכתב את התוכנית יודע שהיא הייתה אמורה לחשב ממוצע. הכוונה הזו לא קיימת בשום מקום בקוד, ולכן שום כלי לא יכול להשוות אליה את התוצאה. שגיאה לוגית היא הפער בין מה שאמרתם למחשב לעשות לבין מה שרציתם שהוא יעשה.
סיבות נפוצות לשגיאות לוגיות
רוב השגיאות הלוגיות מגיעות מרשימה קצרה של דפוסים.
- טעויות של אחד (off by one). לולאה רצה פעם אחת יותר מדי או פחות מדי.
range(1, 5)מייצר 1, 2, 3 ו-4, כי הסוף לא נכלל. ראו איטרציה. - סדר פעולות.
a + b / 2מחלק רק אתb, כמו בממוצע שלמעלה. - השוואה לא נכונה.
<במקום שהיה צריך<=, אוandבמקום שהיה צריךor. תנאים הם ביטויים בוליאניים, ואופרטור שגוי אחד הופך את התוצאה עבור חלק מהקלטים. - תנאים בסדר הלא נכון. בשרשרת של
ifו-elif, התנאי הראשון שהוא אמת מנצח, כך שבדיקה רחבה שמופיעה ראשונה מסתירה את הצרות יותר שמתחתיה. - המשתנה הלא נכון. מעדכנים את
totalבתוך לולאה אבל מדפיסים אתsubtotal. - הנחות על מספרים.
0.1 + 0.2 == 0.3הואFalseב-Python, ב-Java וב-JavaScript, כי מספרי נקודה צפה הם קירובים.7 // 2הוא 3, לא 3.5.
הנה טעות סדר התנאים. ציון 95 אמור להיות A:
D
D
F
95 גדול או שווה ל-60, ולכן הענף הראשון מנצח וה-elif אף פעם לא מגיע. שימו את הסף הגבוה ביותר ראשון, וכל התוצאות נעשות נכונות.
סוגי שגיאות בתכנות
בדרך כלל ממיינים שגיאות תכנות לשלושה סוגים, לפי מתי הן מופיעות ומי מדווח עליהן.
| שגיאת תחביר | שגיאת זמן ריצה | שגיאה לוגית | |
|---|---|---|---|
| מתי היא מופיעה | לפני שהתוכנית רצה | בזמן שהיא רצה | בזמן שהיא רצה, או שאף פעם לא שמים לב |
| מה מזהה אותה | ה-parser או הקומפיילר | סביבת הריצה או מערכת ההפעלה | אדם או בדיקה |
| האם התוכנית רצה? | לא | עד השורה שנכשלת | כן, עד הסוף |
| הודעת שגיאה | כן, עם מספר שורה | כן, עם traceback | אין |
| דוגמה ב-Python | if x > 3 בלי הנקודתיים | 10 / 0 | a + b / 2 לממוצע |
| איך מוצאים אותה | קוראים את ההודעה | קוראים את ה-traceback | משווים את הפלט לתשובה ידועה |
יש ספרי לימוד שמונים סוגים נוספים, ורובם נכנסים בתוך השלושה האלה. שגיאת טיפוס שהקומפיילר של Java דוחה, כמו incompatible types: String cannot be converted to int, מתגלה בזמן קומפילציה כמו שגיאת תחביר, ויש ספרים שקוראים לה שגיאה סמנטית. שגיאת linker קורית בשלב האחרון של בניית תוכנית C או C++, כשהוכרז על פונקציה אבל הקוד שלה לא נמצא בשום מקום. שגיאות חשבון, משאבים וקבצים, כמו חלוקה באפס, מחסור בזיכרון או פתיחת קובץ שלא קיים, הן כולן שגיאות זמן ריצה. יש קורסים שמשתמשים במונח "שגיאה סמנטית" גם כשם נוסף לשגיאה לוגית, אז בדקו לאיזו משמעות ספר לימוד מתכוון.
איך מוצאים שגיאה לוגית
- בדקו עם תשובה שכבר ידועה לכם. חשבו ידנית את התוצאה הנכונה לקלט קטן, ואז השוו. קל יותר לבדוק שלושה ציונים משלושת אלפים.
- הדפיסו את הערכים שבדרך. הדפסה של
scoreושל הענף שנבחר, או של מונה הלולאה בכל מעבר, מראה את הצעד המדויק שבו המציאות סוטה מהתוכנית שלכם. - עברו על הקוד עם דיבאגר. הצבת breakpoint והרצה של שורה אחת בכל פעם עושות את אותו הדבר בלי לערוך את הקוד.
- בדקו את הקצוות. נסו 0, 1, הערך הגדול ביותר, רשימה ריקה והסף המדויק (60 ו-90 בדוגמת הציונים).
- הסבירו את הקוד בקול. תיאור של כל שורה למישהו אחר, או לברווז גומי, מכריח אתכם לומר מה השורה עושה ולא מה אתם מניחים שהיא עושה.
assert הופך תשובה ידועה לבדיקה אוטומטית. הוא לא עושה כלום כשהתנאי אמת, ועוצר את התוכנית כשהוא שקר:
Traceback (most recent call last):
File "main.py", line 10, in <module>
assert grade(95) == "A", "95 should be an A"
^^^^^^^^^^^^^^^^
AssertionError: 95 should be an A
בדיקה שנכשלת הופכת שגיאה לוגית שקטה לשגיאה רועשת עם מספר שורה. זה כל הרעיון שמאחורי בדיקות יחידה (unit testing).
שגיאות לוגיות בשפות אחרות
הדפוסים זהים בכל מקום, אבל לכל שפה יש מלכודות משלה. ב-JavaScript, "5" + 3 הוא המחרוזת "53", ואילו "5" - 3 הוא המספר 2, כך שערך שנקרא מטופס כטקסט יכול להיסכם לא נכון בלי שום שגיאה. ב-C, if (x = 5) משים 5 ל-x ותמיד אמת. Clang מזהיר על זה כברירת מחדל (using the result of an assignment as a condition without parentheses), אבל הקוד עדיין עובר קומפילציה ורץ, אז התייחסו לאזהרות של הקומפיילר ברצינות כמו לשגיאות.
לאן ממשיכים מכאן
השוו את העמוד הזה לעמודים על שגיאת תחביר ועל שגיאת זמן ריצה כדי לראות איך מדווחים על כל סוג. בלולאות גרות טעויות של אחד, ולכן העמוד על איטרציה והמדריך של Python ללולאות for הם קריאה טובה להמשך. כדי לתרגל מציאת תוצאות שגויות בתרגילים אמיתיים, נסו את קורס Python.
שאלות נפוצות
מה ההבדל בין שגיאת תחביר לשגיאה לוגית?
מה זו שגיאה לוגית ב-Python?
range(1, 5) כשרציתם 1 עד 5 כולל, a + b / 2 כשרציתם (a + b) / 2, וענפי if שנבדקים בסדר הלא נכון. Python לא יכולה לזהות אותן, כי אין לה דרך לדעת למה התכוונתם.