راه
۵ کیو· متوسط رو به بالامتوسطPYTHON۴ ثانیه · ۲۵۶ مگابایت

کلاس Person

کلاس Consts و کلاس Person را در همین یک فایل بنویس. داور برای آزمودن calc یک زیرکلاس کوچک از Person و یک محل کار آزمایشی (فقط با level) می‌سازد؛ نیازی به فایل work_place.py نیست.

در این بخش، به سراغ پیاده‌سازی اولین کلاس بنیادین در مدل‌سازی کشور کوئرا، یعنی کلاس Person (فرد)، می‌رویم. این کلاس به‌عنوان پایه‌ای برای انواع مختلف افراد در مدل ما عمل می‌کند و ویژگی‌ها و رفتارهای مشترک آن‌ها را در بر می‌گیرد.

کد کلاس Person در فایل person.py قرار خواهد گرفت.


ثابت‌های پروژه: کلاس Consts

در طول پروژه، از مقادیر ثابتی مانند هزینه‌های پایه برای زندگی یا استخدام استفاده می‌کنیم. برای سازماندهی این مقادیر، یک کلاس ساده به نام Consts تعریف می‌شود که این مقادیر ثابت را در خود نگه می‌دارد. بخشی از این کلاس که مربوط به قیمت‌های پایه‌ی کارکنان است، به‌صورت زیر تعریف می‌شود. در این قسمت از پروژه از این مقادیر استفاده نمی‌کنیم.

python
class Consts:
    BASE_PRICE = {'worker': 1200, 'teacher': 1500, 'engineer': 2000}
    BASE_COST = {'worker': 200, 'teacher': 150, 'engineer': 300}
    BASE_INCOME = {'worker': {'mine': 800}, 'teacher': {'mine': 300}, 'engineer': {'mine': 1000}}
    MIN_AGE = 15
    AGE_MUL = 10

کلاس Person

  • instances: یک متغیر کلاس است، به این معنی که تنها یک کپی از آن وجود دارد که بین تمام اشیاء (نمونه‌های) ساخته شده از کلاس Person به اشتراک گذاشته می‌شود. هدف آن نگهداری لیستی از تمام اشیاء Person است که تاکنون ایجاد شده‌اند.
  • name: نام فرد و از نوع رشته است.
  • age: سن فرد و از نوع عدد صحیح است.
  • level: سطح تجربه یا مهارت فرد است. از نوع عدد صحیح است و با مقدار اولیه‌ی ۱ شروع می‌شود.
  • job: نوع شغل فرد است، از نوع رشته است و با مقدار اولیه‌ی "" (رشته‌ی خالی) شروع می‌شود.
  • work_place: شیء محل کار که فرد در آن مشغول است. از نوع WorkPlace است؛ اما با مقدار اولیه‌ی None شروع می‌شود.

متد سازنده: init(self, name, age)

  • پارامترهای name و age برای مقداردهی اولیه ویژگی‌های متناظر شیء استفاده می‌شوند.
  • ویژگی level با مقدار پیش‌فرض 1 مقداردهی می‌شود.
  • ویژگی‌های job و work_place به ترتیب با "" و None مقداردهی اولیه می‌شوند، زیرا فرد در لحظه‌ی ایجاد هنوز شغل یا محل کار مشخصی ندارد.
  • شیء self باید به لیست Person.instances اضافه شود تا ردیابی تمام افراد امکان‌پذیر باشد.

متد do_level(self, income)

این متد مسئول اعمال تأثیر سطح فرد (self.level) و سطح محل کار (self.work_place.level) بر روی درآمد پایه‌ی فرد (income) است. این متد مقدار نهایی درآمد تعدیل‌شده با سطح را برمی‌گرداند. فرمول محاسبه به شرح زیر است:

income × √(self.level × self.work_place.level)

💡 نکته: پیاده‌سازی این متد (و متد calc که از آن استفاده می‌کند) فرض می‌کند که ویژگی self.work_place هنگام فراخوانی این متد، None نیست و به یک شیء WorkPlace معتبر اشاره می‌کند که دارای ویژگی level است. در یک برنامه‌ی واقعی، برای مدیریت افراد بیکار، نیاز به افزودن بررسی if self.work_place is not None: خواهید داشت. اما برای این تمرین، فرض بر این است که این متد تنها برای افراد شاغل فراخوانی می‌شود یا منطق کل برنامه این وضعیت را قبل از فراخوانی مدیریت می‌کند.

متدهای calc_income() و calc_life_cost()

این دو متد برای محاسبه‌ی درآمد روزانه و هزینه‌ی زندگی فرد در نظر گرفته شده‌اند.

در کلاس پایه‌ی Person، پیاده‌سازی این متدها با کلمه‌ی کلیدی pass انجام می‌شود؛ زیرا منطق واقعی محاسبه درآمد و هزینه زندگی به نوع شغل فرد وابسته است (مثلاً یک مهندس با یک معلم متفاوت درآمد دارد). پیاده‌سازی اصلی این متدها در زیرکلاس‌های Engineer، Teacher و Worker انجام خواهد شد.

سیستم داوری این پیاده‌سازی‌های خاص شغل را هنگام تست به کد شما اضافه می‌کند. شما فقط نیاز دارید که این متدها را در کلاس Person با pass تعریف کنید.

متد calc(self)

این متد وضعیت مالی خالص روزانه فرد را محاسبه می‌کند. برای این کار، ابتدا درآمد پایه‌ی فرد را با فراخوانی self.calc_income() و هزینه‌ی زندگی او را با فراخوانی self.calc_life_cost() به دست می‌آورد. سپس درآمد پایه را با استفاده از متد self.do_level() بر اساس سطح فرد و محل کار تعدیل می‌کند. در نهایت، هزینه‌ی زندگی را از درآمد تعدیل‌شده کم کرده و نتیجه (درآمد خالص یا زیان) را برمی‌گرداند.

متد calc_all()

این متد به‌عنوان یک متد ایستا (Static Method) تعریف شده‌است. هدف این متد، محاسبه‌ی مجموع وضعیت مالی روزانه تمام افرادی است که در مدل ما وجود دارند. برای این کار، این متد روی لیست Person.instances (که شامل تمام اشیاء Person است) پیمایش می‌کند و برای هر شیء، متد calc() آن فرد را فراخوانی کرده و نتایج را با هم جمع می‌بندد و در نهایت، مقدار مجموع نهایی را برمی‌گرداند.

متد get_job(self)

این متد، رشته‌ی شغل فعلی فرد (self.job) را برمی‌گرداند.

متد upgrade(self)

این متد سطح تجربه‌ی فرد (self.level) را یک واحد افزایش می‌دهد. این متد هیچ مقداری را برنمی‌گرداند.

python
def __init__(self, name, age):
    self.name = name
    self.age = age
    self.level = 1
    self.job = ""
    self.work_place = None
    Person.instances.append(self)
python
def do_level(self, income):
    import math
    return income * math.sqrt(self.level * self.work_place.level)
python
def calc_income(self):
    pass

def calc_life_cost(self):
    pass
python
def calc(self):
    income = self.calc_income()
    cost = self.calc_life_cost()
    return self.do_level(income) - cost
python
@staticmethod
def calc_all():
    total = 0
    for person in Person.instances:
        total += person.calc()
    return total
python
def get_job(self):
    return self.job
python
def upgrade(self):
    self.level += 1

💡 چالش‌های حل تمرین

⚠️ چگونه می‌توانم به ویژگی instances دسترسی داشته باشم؟

ویژگی instances مربوط به کلاس است (نه به شیء)؛ بنابراین از طریق Person.instances می‌توان به این ویژگی دسترسی داشت.

⚠️ مشکلات متداول

  • در هیچ‌کدام از توابع نباید مقداری را چاپ کنید، بلکه باید مقادیر خواسته شده را با استفاده از return برگردانید.
  • مطمئن شوید که کتابخانه‌ی math را برای استفاده از math.sqrt ایمپورت کرده‌اید.

✅ این تمرین را در ویرایشگر خود پیاده‌سازی کنید. به یاد داشته باشید که کلاس Person باید در فایل person.py قرار گیرد.

نمونه‌ها

ورودی نمونه ۱
ali = Person("Ali", 20)
[ali.name, ali.age, ali.level, ali.job, ali.work_place]
Person.instances[-1] is ali
خروجی نمونه ۱
['Ali', 20, 1, '', None]
True
ورودی نمونه ۲
a = Person("A", 30)
b = Person("B", 40)
[p.name for p in Person.instances]
خروجی نمونه ۲
['A', 'B']
ورودی نمونه ۳
class Place:
    level = 4

sara = Person("Sara", 30)
sara.work_place = Place()
sara.upgrade()
sara.level
sara.do_level(100)
خروجی نمونه ۳
2
282.842712474619
ورودی نمونه ۴
class Place:
    level = 1

class Coder(Person):
    def calc_income(self):
        return 1000

    def calc_life_cost(self):
        return 300

reza = Coder("Reza", 25)
reza.work_place = Place()
reza.calc()
خروجی نمونه ۴
700.0
ورودی نمونه ۵
class Place:
    def __init__(self, level):
        self.level = level

class Coder(Person):
    def calc_income(self):
        return 400

    def calc_life_cost(self):
        return 100

one = Coder("One", 20)
one.work_place = Place(1)
two = Coder("Two", 30)
two.work_place = Place(9)
Person.calc_all()
خروجی نمونه ۵
1400.0
ورودی نمونه ۶
p = Person("Mina", 22)
p.job = "teacher"
p.get_job()
p.upgrade() is None
خروجی نمونه ۶
'teacher'
True

برای نوشتن پاسخ و دریافت امتیاز، ابتدا وارد حساب شوید.

ورود