# אמיתיוּת לפני לוגיקה, הערכים שעליהם לוגיקה פועלת. ל־Perl אין טיפוס בוליאני ייעודי. כל סקלר הוא או *אמת* או *שקר* כאשר משתמשים בו בהקשר בוליאני, והכלל קצר: > סקלר הוא **שקר** אם הוא אחד מארבעת הערכים `undef`, המספר השלם `0`, המחרוזת `""`, או המחרוזת `"0"`. כל דבר אחר הוא **אמת**. ארבעה ערכי שקר, כל סקלר אחר — לרבות המחרוזות `"00"`, `"0.0"`, `"0E0"`, ו־`"false"` — הוא אמת. ```perl if (0) { ... } # false -- the integer zero if (0.0) { ... } # false -- numerically zero if ("") { ... } # false -- empty string if ("0") { ... } # false -- the string "0" if (undef) { ... } # false -- undefined value if ("00") { ... } # TRUE -- non-empty, not the string "0" if ("0.0") { ... } # TRUE -- non-empty, not the string "0" if ("0 but true") { ... } # TRUE -- non-empty, not the string "0" if (" ") { ... } # TRUE -- single space is non-empty if ("false") { ... } # TRUE -- it's just a 5-character string ``` הניב `"0 but true"` אינו בדיחה. חלק מממשקי ה־API של Perl מחזירים ערך שחייב להשוות שווה לאפס מספרית (כך שבדיקה אריתמטית עושה את הדבר הנכון) אך להיות אמת בהקשר בוליאני. המקרה הקלאסי הוא `ioctl()` — הצלחה המחזירה אפס מילולי הייתה נבדקת כשקר. המחרוזת `"0 but true"` היא אפס מספרית (עם אזהרה המודחקת בהסכמה היסטורית) ובוליאנית־אמת מכיוון שאינה בקבוצת השקר בעלת ארבעת האיברים. ```perl my $rc = ioctl($fh, $cmd, $buf); $rc == 0 and warn "numeric zero"; # would fire on success $rc or warn "boolean false"; # FIRES if API returned 0 # but NOT if "0 but true" ``` ## שני סוגים של השוואה ל־Perl יש משפחות מקבילות של אופרטורי השוואה מפני שיש לה תפיסות מקבילות של שוויון. מספרים מושווים מספרית; מחרוזות מושוות לקסיקוגרפית. המשפחה הלא־נכונה על הטיפוס הלא־נכון היא אחד הבאגים השכיחים ביותר ב־Perl למתחילים. | בדיקה | מספרי | מחרוזת | |-------------------|---------|----------| | שווה | `==` | `eq` | | לא שווה | `!=` | `ne` | | קטן מ | `<` | `lt` | | גדול מ | `>` | `gt` | | קטן או שווה | `<=` | `le` | | גדול או שווה | `>=` | `ge` | | תלת־כיווני (sort) | `<=>` | `cmp` | `==` על מחרוזות מצליח תמיד עבור כל שתי מחרוזות לא־מספריות — שתיהן מומרות ל־`0`, ו־`0 == 0` הוא אמת: ```perl "foo" == "bar"; # TRUE -- both stringify to numeric 0 "foo" eq "bar"; # FALSE -- the actual question "10" eq 10; # TRUE -- string "10" equals numeric 10 stringified "10" == 10; # TRUE -- 10 == 10 numerically "10" lt "9"; # TRUE -- lexical: "1" < "9" "10" < "9"; # FALSE -- numeric: 10 > 9 ``` `<=>` ו־`cmp` מחזירים `-1`, `0`, או `+1` — הצורה הסטנדרטית של מנגנון השוואה למיון. אלה אינם אופרטורים בוליאניים במובן המחמיר, אך הם מופיעים בהקשרים בוליאניים לעיתים מספיק קרובות שכדאי להכיר אותם. ## מדוע זה חשוב ללוגיקה כל אופרטור בוליאני ב־Perl — `&&`, `||`, `//`, `!`, `xor`, `and`, `or`, `not` — משתמש בקבוצת השקר בעלת ארבעת הערכים שלעיל ככלל הקלט שלו. בכל פעם שפרק להלן אומר ״אם `$x` הוא שקר״, זו בדיוק המשמעות: `$x` הוא `undef`, `0`, `""`, או `"0"`. בכל פעם שהוא אומר ״אם `$x` הוא אמת״, `$x` הוא כל דבר אחר. שתי השלכות שכדאי לזכור: 1. **סקלר יכול להיות אמת מבלי להיות ערך־אמת בוליאני.** מחרוזות, הפניות, עצמים שעברו bless, מספרים גדולים — כולם אמת. כאשר אתם שואלים ״האם זה אמת?״ אינכם שואלים ״האם זה שווה ל־1?״ — אתם שואלים ״האם זה לא בקבוצת השקר?״. 2. **התוצאה של אופרטור בוליאני אינה תמיד 1 או 0.** הפרק הבא מכסה זאת בפירוט. בקצרה: `&&` ו־`||` מחזירים אחד מ־ *האופרנדים* שלהם, לא ערך בוליאני מנורמל. זוהי תכונה, לא תופעת לוואי, וניבים רבים של Perl תלויים בה. ## ראו גם - [perlop — השוואה מספרית](../../p5/core/perlop/numeric-comparison.md) ו־[השוואת מחרוזות](../../p5/core/perlop/string-comparison.md) — דפי מדריך העיון עבור `==`/`eq` ושאר משפחות ההשוואה שהוצגו לעיל.