Загрузка данных
import json
from typing import List, Union
class Vehicle:
"""Базовый класс для описания транспортного средства[span_3](start_span)[span_3](end_span)."""
def __init__(
self, brand: str, model: str, year: int, mileage: int = 0
) -> None:
"""Инициализация атрибутов транспортного средства[span_4](start_span)[span_4](end_span)."""
self.brand: str = brand
self.model: str = model
self.year: int = year
self.__mileage: int = max(0, mileage) # Приватный атрибут[span_5](start_span)[span_5](end_span)
@property
def mileage(self) -> int:
"""Геттер для получения значения приватного пробега[span_6](start_span)[span_6](end_span)."""
return self.__mileage
@mileage.setter
def mileage(self, value: int) -> None:
"""Сеттер с проверкой: запрещает уменьшение пробега[span_7](start_span)[span_7](end_span)[span_8](start_span)[span_8](end_span)."""
if value < self.__mileage:
print(
f"Предупреждение: нельзя уменьшить пробег (текущий: {self.__mileage} км, попытались поставить: {value} км)!"
) #[span_9](start_span)[span_9](end_span)
return
self.__mileage = value
def reset_mileage(self) -> None:
"""Сброс пробега в 0 с выводом предупреждения[span_10](start_span)[span_10](end_span)."""
print(
f"Внимание: сброс одометра для {self.brand} {self.model}! Старый пробег был: {self.__mileage} км."
) #[span_11](start_span)[span_11](end_span)
self.__mileage = 0
def drive(self, km: int) -> None:
"""Увеличивает пробег транспортного средства[span_12](start_span)[span_12](end_span)."""
if km < 0:
raise ValueError(
"Количество километов не может быть отрицательным."
) #[span_13](start_span)[span_13](end_span)
self.mileage += km
def get_info(self) -> str:
"""Возвращает строку с базовой информацией о ТС[span_14](start_span)[span_14](end_span)."""
return (
f"{self.year} {self.brand} {self.model}, пробег: {self.mileage} км"
) #[span_15](start_span)[span_15](end_span)
def transport_type(self) -> str:
"""Возвращает тип транспортного средства[span_16](start_span)[span_16](end_span)."""
return "общий транспорт" #[span_17](start_span)[span_17](end_span)
def to_dict(self) -> dict:
"""Преобразует объект в словарь для сериализации в JSON[span_18](start_span)[span_18](end_span)."""
return {
"type": "Vehicle",
"brand": self.brand,
"model": self.model,
"year": self.year,
"mileage": self.mileage,
}
@staticmethod
def from_dict(data: dict) -> "Vehicle":
"""Создает объект Vehicle из словаря[span_19](start_span)[span_19](end_span)."""
return Vehicle(
brand=data["brand"],
model=data["model"],
year=data["year"],
mileage=data["mileage"],
)
class Car(Vehicle):
"""Подкласс легкового автомобиля[span_20](start_span)[span_20](end_span)."""
def __init__(
self,
brand: str,
model: str,
year: int,
fuel_type: str,
mileage: int = 0,
) -> None:
"""Инициализация атрибутов легкового автомобиля[span_21](start_span)[span_21](end_span)."""
super().__init__(brand, model, year, mileage)
self.fuel_type: str = fuel_type #[span_22](start_span)[span_22](end_span)
def refuel(self, liters: float) -> None:
"""Метод для моделирования заправки авто[span_23](start_span)[span_23](end_span)."""
print(
f"Автомобиль {self.brand} {self.model} заправлен на {liters} л. ({self.fuel_type})."
) #[span_24](start_span)[span_24](end_span)
def get_info(self) -> str:
"""Переопределенный метод получения информации о легковом авто[span_25](start_span)[span_25](end_span)."""
base_info = super().get_info()
return f"{base_info}, тип топлива: {self.fuel_type}" #[span_26](start_span)[span_26](end_span)
def transport_type(self) -> str:
"""Возвращает тип транспортного средства[span_27](start_span)[span_27](end_span)."""
return "легковой" #[span_28](start_span)[span_28](end_span)
def to_dict(self) -> dict:
"""Преобразует объект Car в словарь[span_29](start_span)[span_29](end_span)."""
data = super().to_dict()
data["type"] = "Car"
data["fuel_type"] = self.fuel_type
return data
@staticmethod
def from_dict(data: dict) -> "Car":
"""Создает объект Car из словаря[span_30](start_span)[span_30](end_span)."""
return Car(
brand=data["brand"],
model=data["model"],
year=data["year"],
fuel_type=data["fuel_type"],
mileage=data["mileage"],
)
class Truck(Vehicle):
"""Подкласс грузового автомобиля[span_31](start_span)[span_31](end_span)."""
def __init__(
self,
brand: str,
model: str,
year: int,
cargo_capacity: float,
mileage: int = 0,
) -> None:
"""Инициализация атрибутов грузовика[span_32](start_span)[span_32](end_span)."""
super().__init__(brand, model, year, mileage)
self.cargo_capacity: float = cargo_capacity #[span_33](start_span)[span_33](end_span)
def load_cargo(self, tons: float) -> None:
"""Загрузка груза с проверкой превышения грузоподъемности[span_34](start_span)[span_34](end_span)."""
if tons > self.cargo_capacity:
print(
f"Ошибка: Нельзя загрузить {tons} т! Превышена грузоподъёмность ({self.cargo_capacity} т)."
) #[span_35](start_span)[span_35](end_span)
else:
print(
f"Успешно загружено {tons} т в грузовик {self.brand} {self.model}."
) #[span_36](start_span)[span_36](end_span)
def get_info(self) -> str:
"""Переопределенный метод получения информации о грузовике[span_37](start_span)[span_37](end_span)."""
base_info = super().get_info()
return f"{base_info}, грузоподъёмность: {self.cargo_capacity} т" #[span_38](start_span)[span_38](end_span)
def transport_type(self) -> str:
"""Возвращает тип транспортного средства[span_39](start_span)[span_39](end_span)."""
return "грузовик" #[span_40](start_span)[span_40](end_span)
def to_dict(self) -> dict:
"""Преобразует объект Truck в словарь[span_41](start_span)[span_41](end_span)."""
data = super().to_dict()
data["type"] = "Truck"
data["cargo_capacity"] = self.cargo_capacity
return data
@staticmethod
def from_dict(data: dict) -> "Truck":
"""Создает объект Truck из словаря[span_42](start_span)[span_42](end_span)."""
return Truck(
brand=data["brand"],
model=data["model"],
year=data["year"],
cargo_capacity=data["cargo_capacity"],
mileage=data["mileage"],
)
def deserialize_vehicle(data: dict) -> Vehicle:
"""Вспомогательная функция для восстановлении объектов нужного класса из JSON[span_43](start_span)[span_43](end_span)."""
v_type = data.get("type")
if v_type == "Car":
return Car.from_dict(data)
elif v_type == "Truck":
return Truck.from_dict(data)
return Vehicle.from_dict(data)
if __name__ == "__main__":
print("=== Задание 1. Базовый класс и объекты ===")
v1 = Vehicle("Toyota", "Camry", 2024, 45000) #[span_44](start_span)[span_44](end_span)
v2 = Vehicle("Ford", "Focus", 2020, 80) #[span_45](start_span)[span_45](end_span)
v1.drive(120) #[span_46](start_span)[span_46](end_span)
print(v1.get_info()) #[span_47](start_span)[span_47](end_span)
print(v2.get_info()) #[span_48](start_span)[span_48](end_span)
print("\n=== Задание 2. Наследование ===")
car1 = Car("BMW", "X5", 2022, "Бензин", 15000) #[span_49](start_span)[span_49](end_span)
truck1 = Truck("Volvo", "FH16", 2021, 20.0, 100000) #[span_50](start_span)[span_50](end_span)
car1.refuel(50) #[span_51](start_span)[span_51](end_span)
truck1.load_cargo(15.0) #[span_52](start_span)[span_52](end_span)
truck1.load_cargo(25.0) # Проверка превышения грузоподъемности[span_53](start_span)[span_53](end_span)
print(car1.get_info()) #[span_54](start_span)[span_54](end_span)
print(truck1.get_info()) #[span_55](start_span)[span_55](end_span)
print("\n=== Задание 3. Инкапсуляция и свойства ===")
print(f"Текущий пробег v1: {v1.mileage} км") #[span_56](start_span)[span_56](end_span)
v1.mileage = 40000 # Попытка уменьшить пробег -> должно выдать предупреждение[span_57](start_span)[span_57](end_span)
v1.mileage = 46000 # Успешное увеличение
print(f"Обновленный пробег v1: {v1.mileage} км")
v1.reset_mileage() # Сброс пробега[span_58](start_span)[span_58](end_span)
print(f"Пробег v1 после сброса: {v1.mileage} км")
print("\n=== Задание 4. Полиморфизм и список объектов ===")
fleet: List[Vehicle] = [
Vehicle("Hyundai", "Solaris", 2019, 60000),
Car("Audi", "A6", 2023, "Дизель", 12000),
Truck("KAMAZ", "5490", 2020, 18.0, 150000),
Car("Tesla", "Model 3", 2024, "Электричество", 5000),
Truck("MAN", "TGX", 2018, 22.5, 210000),
] #[span_59](start_span)[span_59](end_span)
for item in fleet:
print(
f"[{item.transport_type()}] {item.get_info()}"
) # Вызов через полиморфизм[span_60](start_span)[span_60](end_span)
print("\n=== Задание 5 (Вариант Б). Сохранение состояния в JSON ===")
filename = "vehicles.json"
# Сериализация списка объектов в JSON-файл[span_61](start_span)[span_61](end_span)
json_data = [item.to_dict() for item in fleet]
with open(filename, "w", encoding="utf-8") as f:
json.dump(json_data, f, ensure_ascii=False, indent=4)
print(f"Данные сохранены в файл {filename}")
# Загрузка и восстановление объектов из JSON-файла[span_62](start_span)[span_62](end_span)
with open(filename, "r", encoding="utf-8") as f:
loaded_data = json.load(f)
restored_fleet = [deserialize_vehicle(item) for item in loaded_data]
print("\nВосстановленные объекты из JSON:")
for obj in restored_fleet:
print(f"({type(obj).__name__}) {obj.get_info()}")