במדריך זה, נלמד על הסוגים הקבועים וכיצד הם עוזרים לשפר את קריאות הקוד. אם אינך מכיר, הקבועים הם השמות המייצגים ערכים שאינם משתנים במהלך הפעלת התוכנית. הם המושג הבסיסי הנפוץ ביותר בתכנות. עם זאת, לפייתון אין תחביר ייעודי להגדרת קבועים. באופן כללי, קבועי Python הם משתנים שלעולם אינם משתנים. נקיים דיון מפורט על הקבוע של Python בסעיף הקרוב.
מה הם קבועים?
בדרך כלל, נעשה שימוש במונח קבוע במתמטיקה, ערך או כמות שלעולם לא משתנה. בתכנות, קבוע מתייחס לשם המשויך לערך שלעולם לא משתנה במהלך ביצוע התכנות. קבוע תכנות שונה מקבועים אחרים, והוא מורכב משני דברים - שם וערך משויך. השם יתאר על מה הקבוע, והערך הוא הביטוי הקונקרטי של הקבוע עצמו.
ברגע שהגדרנו את הקבוע, נוכל לגשת רק לערכו אך לא ניתן לשנות אותו לאורך זמן. עם זאת, אנו יכולים לשנות את הערך של המשתנה. דוגמה מהחיים האמיתיים היא - מהירות האור, מספר הדקות בשעה, ושם תיקיית השורש של הפרויקט.
למה להשתמש ב-Constant?
בשפות תכנות, Constants מאפשרים לנו להגן מפני שינוי ערכם בטעות, מה שעלול לגרום לשגיאות שקשה לאפות באגים. זה גם מועיל להפוך את הקוד ליותר קריא וניתן לתחזוקה. בואו נראה כמה יתרונות של קבוע.
קבועים בהגדרת משתמש
עלינו להשתמש במוסכמות השמות ב-Python כדי להגדיר את הקבוע ב-Python. עלינו לכתוב את השם באותיות גדולות עם קווים תחתונים המפרידים בין מילים.
להלן הדוגמה של קבועי Python המוגדרים על ידי המשתמש -
PI = 3.14 MAX_SPEED = 300 DEFAULT_COLOR = ' 33[1;34m' WIDTH = 20 API_TOKEN = '567496396372' BASE_URL = 'https://api.example.com' DEFAULT_TIMEOUT = 5 BUILTINS_METHODS = ('sum', 'max', 'min', 'abs') INSTALLED_APPS = [ 'django.contrib.admin', 'django.contrib.auth', 'django.contrib.contenttypes', ... ]
השתמשנו באותה דרך שבה אנחנו יוצרים משתנים ב- Python. אז אנחנו יכולים להניח שקבועי פייתון הם רק משתנים, וההבחנה היחידה היא שהקבוע משתמש באותיות רישיות בלבד.
שימוש באותיות רישיות הופך את הקבוע לבלוט מהמשתנים שלנו ומהווה תרגול שימושי או מועדף.
לעיל דנו במשתמשים המוגדרים על ידי המשתמש; Python מספקת גם מספר שמות פנימיים שיכולים להתייחס אליהם וצריכים להתייחס אליהם כאל קבועים.
קבועים חשובים בפייתון
בחלק זה, נלמד על כמה קבועים פנימיים המשמשים כדי להפוך את קוד Python לקריא יותר. בואו נבין כמה קבועים חשובים.
קבועים מובנים
בתיעוד הרשמי, ה נָכוֹן ו שֶׁקֶר רשומים בתור הקבוע הראשון. אלו הם ערכי Python Boolean והם המופע של int. א נָכוֹן יש ערך של 1, ו שֶׁקֶר יש ערך 0.
דוגמא -
>>> True True >>> False False >>> isinstance(True, int) True >>> isinstance(False, int) True >>> int(True) 1 >>> int(False) 0 >>> True = 42 ... SyntaxError: cannot assign to True >>> True is True True >>> False is False True
זכור ששמות אמיתיים ושמות לא נכון הם קבועים קפדניים. במילים אחרות, אנחנו לא יכולים להקצות אותם מחדש, ואם ננסה להקצות אותם מחדש, נקבל שגיאת תחביר. שני הערכים הללו הם אובייקטים בודדים ב- Python, כלומר קיים רק מופע אחד.
שמות דאנדר פנימיים
לפייתון יש גם הרבה פנימיים רַעַם שמות שאנו יכולים לראות בקבועים. ישנם כמה מהשמות הייחודיים הללו, נלמד על __name__ ו__file__ בחלק זה.
התכונה __name__ קשורה לאיך להפעיל קטע קוד נתון. בעת ייבוא מודול, Python intern מגדיר את __name__ למחרוזת המכילה את שם המודול.
new_file.py
print(f'The type of __name__ is: {type(__name__)}') print(f'The value of __name__ is: {__name__}')
בשורת הפקודה והקלד את הפקודה הבאה -
python -c 'import new_file'
ה-c משמש לביצוע פיסת קוד קטנה של Python בשורת הפקודה. בדוגמה שלמעלה, ייבאנו את קובץ חדש מודול, המציג כמה הודעות על המסך.
פלט -
The type of __name__ is: The value of __name__ is: timezone
כפי שאנו יכולים לראות שה-__name__ מאחסן את המחרוזת __main__, מציין שאנו יכולים להריץ את קבצי ההפעלה ישירות כתוכנית Python.
מצד שני, לתכונה __file__ יש את הקובץ ש-Python מייבאת או מבצעת כרגע. אם נשתמש בתכונה __file__ בתוך הקובץ, נקבל את הנתיב למודול עצמו.
בואו נראה את הדוגמה הבאה -
שכבות מודל osi
דוגמא -
print(f'The type of __file__ is: {type(__file__)}') print(f'The value of __file__ is: {__file__}')
תְפוּקָה:
The type of __file__ is: The value of __file__ is: D:Python Project ew_file.py
אנחנו יכולים גם לרוץ ישירות ונקבל את אותה תוצאה.
דוגמא -
print(f'The type of __file__ is: {type(__file__)}') print(f'The value of __file__ is: {__file__}')
תְפוּקָה:
python new_file.py The type of __file__ is: The value of __file__ is: timezone.py
קבועי מחרוזת ומתמטיקה שימושיים
יש הרבה קבועים יקרי ערך בספרייה הסטנדרטית. חלקם מחוברים בקפדנות למודולים, פונקציות ומחלקות ספציפיים; רבים הם כלליים, ואנחנו יכולים להשתמש בהם במספר תרחישים. בדוגמה שלהלן, נשתמש במודולים מתמטיקה ובמודולים הקשורים למחרוזת מתמטיקה ומחרוזת, בהתאמה.
אקראי ג
בואו נבין את הדוגמה הבאה -
דוגמא -
>>> import math >>> math.pi 3.141592653589793 >>> math.tau 6.283185307179586 >>> math.nan nan >>> math.inf inf >>> math.sin(30) -0.9880316240928618 >>> math.cos(60) -0.9524129804151563 >>> math.pi 3.141592653589793
הקבועים הללו ישחקו תפקיד חיוני כאשר אנו כותבים קוד הקשור למתמטיקה או מבצעים חישובים ספציפיים.
בואו נבין את הדוגמה הבאה -
דוגמא -
import math class Sphere: def __init__(self, radius): self.radius = radius def area(self): return math.pi * self.radius**2 def perimeter(self): return 2 * math.pi * self.radius def projected_volume(self): return 4/3 * math.pi * self.radius**3 def __repr__(self): return f'{self.__class__.__name__}(radius={self.radius})'
בקוד לעיל, השתמשנו ב- math.pi במקום מנהג פאי קבועים. הקבוע הקשור למתמטיקה מספק יותר הקשרים לתוכנית. היתרון בשימוש בקבוע math.pi הוא שאם אנחנו משתמשים בגרסה ישנה יותר של Python, נקבל גרסת 32 סיביות של Pi. אם נשתמש בתוכנית לעיל בגרסה המודרנית של Python, נקבל גרסת 64 סיביות של pi. אז התוכנית שלנו תתאים את עצמה לסביבת הביצוע הקונקרטית שלה.
מודול המחרוזות מספק גם כמה קבועי מחרוזת מובנים שימושיים. להלן הטבלה של השם והערך של כל קבוע.
שֵׁם | ערך |
---|---|
ascii_אותיות קטנות | אבגדהוזחטיכלמנסעפצקרשת |
ascii_אותיות גדולות | אבגדהוזחטיכלמנסעפצקרשת |
ascii_letters | ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz |
ספרות | 0123456789 |
hexdigits | 0123456789abcdefABCDEF |
אוקטספרות | 01234567 |
אנחנו יכולים להשתמש בקבועים הקשורים למחרוזת בביטויים רגולריים, בעיבוד שפה טבעית, עם הרבה עיבוד מחרוזות ועוד.
קבועים להערת סוגים
מאז Python 3.8, מודול ההקלדה כולל מחלקה Final המאפשרת לנו לכתוב הערות על קבועים. אם נשתמש במחלקה Final כדי להגדיר את הקבועים בתוכנית, נקבל את שגיאת הסוג הסטטית שהבודק mypy בודק והיא תראה שאיננו יכולים להקצות מחדש לשם Final. בואו נבין את הדוגמה הבאה.
דוגמא -
from typing import Final MAX_Marks: Final[int] = 300 MAX_Students: Final[int] = 500 MAX_Marks = 450 # Cannot assign to final name 'MAX_SPEED' mypy(error)
ציינו את המשתנה הקבוע עם ה-Final Class שציינו את שגיאת הסוג כדי לדווח על שגיאה אם שם מוצהר יוקצה מחדש. עם זאת, הוא מקבל דוח על שגיאת בודק סוגים; Python אכן משנה את הערך של MAX_SPEED. אז, Final לא מונע הקצאה מתמיד מקרי בזמן ריצה.
קבועי מיתר
כפי שנדון בסעיף הקודם, Python אינו תומך בקבועים קפדניים; יש לו רק משתנים שלעולם לא משתנים. לכן, קהילת Python פועלת לפי מוסכמות השמות של שימוש באות גדולה כדי לזהות את המשתנים הקבועים.
זה יכול להיות בעיה אם אנחנו עובדים על פרויקט Python גדול עם מתכנתים רבים ברמות שונות. אז זה יהיה נוהג טוב שיהיה מנגנון המאפשר לנו להשתמש בקבועים קפדניים. כפי שאנו יודעים, Python היא שפה דינמית, וישנן מספר דרכים להפוך את הקבועים לבלתי ניתנים לשינוי. בחלק זה נלמד על כמה מהדרכים הללו.
תכונות .__slots__
כיתות Python מספקות את המתקן להשתמש בתכונות __slots__. לחריץ יש את המנגנון המיוחד להקטנת גודל החפצים. זהו מושג של אופטימיזציה של זיכרון על אובייקטים. אם נשתמש בתכונה __slots__ במחלקה, לא נוכל להוסיף את המופע החדש, כי הוא לא משתמש בתכונות __dict__. בנוסף, אין לו א .__dict__ תכונה מרמזת על אופטימיזציה במונחים של צריכת זיכרון. בואו נבין את הדוגמה הבאה.
דוגמה - ללא שימוש בתכונות __slots__
class NewClass(object): def __init__(self, *args, **kwargs): self.a = 1 self.b = 2 if __name__ == '__main__': instance = NewClass() print(instance.__dict__)
פלט -
{'a': 1, 'b': 2}
כל אובייקט ב-Python מכיל מילון דינמי המאפשר הוספת תכונות. מילונים צורכים הרבה זיכרון, והשימוש ב-__slots__ מפחית את בזבוז השטח והזיכרון. בואו נראה דוגמה נוספת.
דוגמא -
Java hasnext
class ConstantsName: __slots__ = () PI = 3.141592653589793 EULER_NUMBER = 2.718281828459045 constant = ConstantsName() print(constant.PI) print(constant.EULER_NUMBER) constant.PI = 3.14 print(constant.PI)
פלט -
3.141592653589793 2.718281828459045 Traceback (most recent call last): File '', line 10, in AttributeError: 'ConstantsName' object attribute 'PI' is read-only
בקוד שלמעלה, אתחלנו את תכונות המחלקה עם תכונות המשבצות. למשתנה יש ערך קבוע, אם ננסה להקצות מחדש את המשתנה נקבל שגיאה.
מעצב @property
אנחנו יכולים גם להשתמש @תכונה דקורטור כדי ליצור מחלקה שפועלת כמרחב שמות עבור קבועים. אנחנו רק צריכים להגדיר את תכונת הקבועים מבלי לספק להם שיטת קבע. בואו נבין את הדוגמה הבאה.
דוגמא -
class ConstantsName: @property def PI(self): return 3.141592653589793 @property def EULER_NUMBER(self): return 2.718281828459045 constant = ConstantsName() print(constant.PI) print(constant.EULER_NUMBER) constant.PI = 3.14 print(constant.PI)
פלט -
3.141592653589793 2.718281828459045 Traceback (most recent call last): File '', line 13, in AttributeError: can't set attribute
הם רק מאפיינים לקריאה בלבד, אם ננסה להקצות מחדש, נקבל AttributeError.
פונקציית המפעל namedtuple()
מודול האיסוף של Python מגיע עם פונקציית המפעל שנקראת namedtuple(). משתמש ב namedtuple() פונקציה, נוכל להשתמש בשדות בעלי השם ובסימוני הנקודה כדי לגשת לפריטים שלהם. אנו יודעים ש-tuples הם בלתי ניתנים לשינוי, מה שאומר שאיננו יכולים לשנות עצם קיים בשם tuple במקום.
בואו נבין את הדוגמה הבאה.
דוגמא -
from collections import namedtuple ConstantsName = namedtuple( 'ConstantsName', ['PI', 'EULER_NUMBER'] ) constant = ConstantsName(3.141592653589793, 2.718281828459045) print(constant.PI) print(constant.EULER_NUMBER) constant.PI = 3.14 print(constant.PI)
פלט -
3.141592653589793 2.718281828459045 Traceback (most recent call last): File '', line 17, in AttributeError: can't set attribute
הדקורטור של @dataclass
כפי ששמה מרמז, מחלקת הנתונים מחזיקה נתונים, הם יכולים להיות מורכבים משיטות, אבל זו לא המטרה העיקרית שלהם. עלינו להשתמש ב-@dataclass decorator כדי ליצור את מחלקות הנתונים. אנחנו יכולים גם ליצור את הקבועים הקפדניים. ה-@dataclass decorator לוקח טיעון קפוא המאפשר לנו לסמן את מחלקת הנתונים שלנו כבלתי ניתנת לשינוי. היתרונות של שימוש ב-@dataclass decorator, איננו יכולים לשנות את תכונת המופע שלו.
בואו נבין את הדוגמה הבאה.
דוגמא -
from dataclasses import dataclass @dataclass(frozen=True) class ConstantsName: PI = 3.141592653589793 EULER_NUMBER = 2.718281828459045 constant = ConstantsName() print(constant.PI) print(constant.EULER_NUMBER) constant.PI = 3.14 print(constant.PI)
פלט -
3.141592653589793 2.718281828459045 Traceback (most recent call last): File '', line 19, in File '', line 4, in __setattr__ dataclasses.FrozenInstanceError: cannot assign to field 'PI'
הסבר -
בקוד לעיל, ייבאנו את ה-@dataclass decorator. השתמשנו במעצב הזה ל-ConstantsName כדי להפוך אותו למחלקת נתונים. הגדרנו את הארגומנט הקפוא ל-True כדי להפוך את מחלקת הנתונים לבלתי ניתנת לשינוי. יצרנו את המופע של מחלקת הנתונים, ואנחנו יכולים לגשת לכל הקבועים אבל לא יכולים לשנות אותם.
השיטה המיוחדת .__setattr__()
Python מאפשר לנו להשתמש בשיטה מיוחדת בשם .__setattr__(). באמצעות שיטה זו, אנו יכולים להתאים אישית את תהליך הקצאת התכונות מכיוון ש-Python קורא לשיטה באופן אוטומטי בכל הקצאת תכונות. בואו נבין את הדוגמה הבאה -
דוגמא -
class ConstantsName: PI = 3.141592653589793 EULER_NUMBER = 2.718281828459045 def __setattr__(self, name, value): raise AttributeError(f'can't reassign constant '{name}'') constant = ConstantsName() print(constant.PI) print(constant.EULER_NUMBER) constant.PI = 3.14 print(constant.PI)
פלט -
3.141592653589793 2.718281828459045 Traceback (most recent call last): File '', line 22, in File '', line 17, in __setattr__ AttributeError: can't reassign constant 'PI'
השיטה __setattr__() לא מאפשרת לבצע שום פעולת הקצאה על תכונות המחלקה. אם ננסה להקצות מחדש, זה פשוט יעלה AttributeError.
סיכום
קבועים משמשים בעיקר ברעיון בתכנות, במיוחד במונח מתמטי. במדריך זה, למדנו על המושגים החשובים של הקבועים והטעמים שלו. קהילת Python משתמשת באותיות גדולות כמוסכמה של שמות כדי לזהות את הקבועים. עם זאת, דנו בכמה דרכים מתקדמות להשתמש בקבועים ב- Python. דנו כיצד לשפר את הקריאות, השימוש החוזר והשמירה של הקוד עם קבועים. הזכרנו כיצד ליישם טכניקות שונות כדי להפוך את קבועי הפייתון שלנו לקבועים בהחלט.