לדלג לתוכן

מה זה טיפוסים בפייתון - type hints מוסבר בפשטות

בואו נדבר בכנות. פייתון היא שפה דינמית - משתנה יכול להכיל מספר עכשיו ומחרוזת בעוד שתי שורות, ואף אחד לא עוצר אתכם. זה חלק ממה שהופך אותה לנוחה ומהירה לכתיבה. אז למה, אם ככה, יש לכם קוד פייתון שמלא בדברים כמו def greet(name: str) -> str:? זה נקרא type hints, רמזי טיפוס, וזה אחד הדברים שהכי מבלבלים מתחילים - כי הם נראים כמו טיפוסים בשפה סטטית, אבל הם לא באמת מתנהגים ככה.

איך כותבים רמז טיפוס

התחביר פשוט - אחרי שם הפרמטר, נקודתיים והטיפוס שלו. אחרי החץ ->, הטיפוס של הערך המוחזר:

def greet(name: str) -> str:
    return f"שלום, {name}"

זה אומר "אני מצפה שהפרמטר name יהיה מחרוזת, ושהפונקציה תחזיר מחרוזת". אפשר גם להוסיף רמז לטיפוס של משתנה רגיל:

age: int = 25
is_active: bool = True

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

אבל זה לא נאכף בזמן ריצה - האמת שרוב ההדרכות מדלגות עליה

הנה החלק שממש חשוב להבין - כתיבת name: str לא גורמת לפייתון לבדוק בפועל שהערך שהועבר הוא מחרוזת. פייתון תריץ את הקוד גם אם תעבירו משהו אחר לגמרי:

def greet(name: str) -> str:
    return f"שלום, {name}"

print(greet(42))  # רץ בלי שגיאה, למרות שרשמנו str

הקוד הזה ירוץ בלי בעיה ויחזיר "שלום, 42", למרות שרשום מפורש שאמור להיכנס str. Type hints הם בדיוק מה שהשם אומר - רמז, לא כלל אכיפה. פייתון פשוט מתעלמת מהם בזמן ריצה. זו נקודה שממש קל לפספס כשמתחילים, כי בשפות אחרות טיפוסים כן נאכפים, ואנשים שבאים משם מצפים לאותה התנהגות.

אז מה הטעם, אם זה לא נאכף

הערך של type hints הוא לא בזמן ריצה, אלא בזמן כתיבת הקוד. עורכי קוד כמו VS Code או PyCharm קוראים את הרמזים האלה ונותנים לכם השלמות אוטומטיות מדויקות יותר, ומתריעים אם משהו נראה לא מתאים - עוד לפני שהרצתם שורת קוד אחת. זה גם הופך את הקוד לתיעוד חי - מסתכלים על חתימת פונקציה ומיד יודעים מה היא מצפה לקבל ומה היא מחזירה, בלי לקרוא את כל הגוף שלה.

הכלי שבאמת אוכף - mypy

אם אתם רוצים אכיפה אמיתית, יש כלי חיצוני בשם mypy שסורק את הקוד שלכם ובודק אם ה-type hints עקביים, בלי בכלל להריץ את התוכנית:

pip install mypy
mypy script.py

אם תריצו את זה על הדוגמה הקודמת עם greet(42), mypy יתריע שהעברתם int למקום שמצפה ל-str. פייתון עצמה עדיין תרוץ בלי בעיה - mypy הוא כלי בדיקה נפרד, לא חלק מהריצה של פייתון. פרויקטים גדולים בדרך כלל מריצים אותו כחלק מתהליך הבדיקות האוטומטי, כדי לתפוס טעויות טיפוס לפני שהן מגיעות לייצור.

טיפוסים נפוצים שכדאי להכיר

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

from typing import Optional

def get_names() -> list[int]:
    return [1, 2, 3]

def get_scores() -> dict[str, int]:
    return {"דנה": 90, "יוסי": 85}

def find_user(user_id: int) -> Optional[str]:
    if user_id == 1:
        return "דנה"
    return None

list[int] אומר רשימה שכל האיברים בה הם מספרים שלמים. dict[str, int] אומר מילון עם מפתחות מחרוזת וערכים מספר שלם. Optional[str] אומר שהערך המוחזר יכול להיות מחרוזת, או None - שימושי מאוד לפונקציות שלפעמים לא מוצאות תוצאה. בגרסאות חדשות של פייתון אפשר גם לכתוב str | None במקום Optional[str], שתי הצורות שקולות.

מתי זה שווה את המאמץ, ומתי לא

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

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

אם אתם עדיין בשלבים הראשונים ורוצים לבנות בסיס יציב לפני שקופצים לתוספות כמו type hints, שווה לעבור על קורס התכנות הבסיסי שלנו - שם בונים קודם את היסודות, ואז אפשר להוסיף שכבות כאלה בביטחון.

ואם יצא לכם קוד עם type hints ש-mypy מתעקש להתלונן עליו ואתם לא מבינים למה - זה בדיוק סוג השאלה שהקהילה בדיסקורד אוהבת לפתור.

הצטרפו לקהילה בדיסקורד