סקלרים ומחרוזות

length#

מחזיר את מספר התווים במחרוזת.

length ממיר את הארגומנט שלו למחרוזת ומחזיר כמה תווים המחרוזת הזו מכילה. ״תווים״ משמעו תווים לוגיים של Perl, לא בתים: מחרוזת המכילה עשר נקודות קוד היא בעלת אורך 10 ללא קשר לכמה בתים אותן נקודות קוד תופסות כאשר הן מקודדות כ־UTF-8 על דיסק או על החוט.

תקציר#

length EXPR
length

מה מקבלים בחזרה#

מספר שלם אי־שלילי - ספירת התווים בערך המומר־למחרוזת של EXPR. אם EXPR מושמט, length פועל על $_. אם EXPR הוא undef, התוצאה היא undef, לא 0; זהו המקרה היחיד שבו length אינו מחזיר מספר, וזה מכוון - זה מאפשר להבחין בין סקלר לא־מוגדר למחרוזת ריקה ללא בדיקת defined נפרדת:

length(undef)       # undef
length("")          # 0
length("abc")       # 3

תווים, לא בתים#

על מחרוזת Perl רגילה, length סופר תווים. ספירת הבתים של אותה מחרוזת מקודדת כ־UTF-8 שונה בדרך כלל והיא מה שמערכות חיצוניות (גדלי קבצים, מטענים של רשת, כותרות Content-Length) רוצות. השיגו אותה על־ידי קידוד תחילה:

use Encode;
my $s     = "na\x{EF}ve";          # five characters
my $chars = length $s;              # 5
my $bytes = length(encode('UTF-8', $s));  # 6

ראו Encode ו־perlunicode לסיפור המלא על איך מחרוזות Perl נושאות דגל פנימי של תווים מול בתים ומתי הדגל הזה משמעותי.

דוגמאות#

ספירה בסיסית:

length "hello"                      # 5
length ""                           # 0

ארגומנט ברירת המחדל הוא $_:

for ("a", "bb", "ccc") {
    print length, "\n";             # 1, 2, 3
}

הבחנה בין לא־מוגדר לריק:

my $x;
my $y = "";
print defined(length $x) ? "set" : "undef", "\n";   # undef
print defined(length $y) ? "set" : "undef", "\n";   # set

מחרוזת Unicode - ספירת תווים מול ספירת בתים:

my $s = "caf\x{E9}";                # four characters, one of them non-ASCII
length $s;                          # 4
length encode('UTF-8', $s);         # 5

מספרים מומרים למחרוזת לפני ספירה, מה ששימושי לעיתים ומפתיע לעיתים:

length 12345                        # 5
length 3.14                         # 4  ("3.14")
length 1e6                          # 7  ("1000000")

מקרי קצה#

  • undef פנימה, undef החוצה. length(undef) מחזיר undef, לא 0. תחת use warnings קריאת סקלר לא־מוגדר דרך length $x היכן ש־$x הוא undef אינה פולטת אזהרת uninitialized, בשונה מרוב האופרטורים האחרים.

  • מערך או האש שלמים: length אינו סופר איברים. הוא ממיר את הארגומנט שלו למחרוזת, ולכן length @arr מעריך תחילה את @arr בהקשר סקלר (ספירת האיברים שלו) ואז סופר את הספרות של אותו מספר. עבור הגודל בפועל השתמשו ב־scalar @arr או scalar keys %hash:

    my @arr = (1) x 100;
    length @arr;                      # 3  (digits of "100")
    scalar @arr;                      # 100
    
  • סקלרים קשורים או קסומים: length מפעיל FETCH, כך שהערך הנספר הוא מה ששכבת ה־tie מחזירה באותו רגע.

  • עצמים בעלי overload: length $obj מפעיל את ה־overload של המרה־למחרוזת "" (או חוזר לצורת ההפניה ברירת המחדל) וסופר תווים במחרוזת התוצאתית.

  • תווים רחבים מקלט בתים: מחרוזת שנקראה ממטפל ללא שכבת קידוד היא מחרוזת בתים. length סופר בתים אז - מכיוון שכל בית הוא תו אחד עבור Perl. פענחו תחילה אם אתם רוצים ספירת תווים:

    open my $fh, "<:raw", $path or die $!;
    my $bytes = do { local $/; <$fh> };
    my $text  = decode('UTF-8', $bytes);
    length $bytes;                    # byte count
    length $text;                     # character count
    
  • Locale ופרגמות: בשונה מ־lc / uc / fc, length אינו משתנה לפי use locale. תו הוא תו ללא קשר.

הבדלים מ־upstream#

תואם מלא ל־upstream Perl 5.42.

ראו גם#

  • scalar - מאלץ הקשר סקלר; הדרך הנכונה לקבל ספירת איברים ממערך (scalar @arr) במקום אורך הספירה המומרת־למחרוזת

  • substr - מחלץ תת־מחרוזת לפי offset של תווים; משתלב באופן טבעי עם length לעבודות פריסה

  • index - מוצא את המיקום של תת־מחרוזת; מחזיר offset של תווים נמדד באותה דרך ש־length מודד

  • sprintf - רוחבי שדה של %s הם ספירות תווים, אותה תפיסה כמו length

  • reverse - בהקשר סקלר הופך מחרוזת תו־אחר־תו; אותו מודל תווים כמו length

  • pos - מיקום התאמת regex, גם הוא בתווים