Практическая работа №7
Основные теоретические положения
Section titled “Основные теоретические положения”1. Собственные и унаследованные свойства
Объект может содержать собственные свойства и получать свойства или методы через прототип.
const user = { name: "Иван",};
console.log(user.name);console.log(user.toString());Свойство name принадлежит самому объекту, а метод toString() доступен через прототипную цепочку.
Проверить собственное свойство можно так:
console.log(Object.hasOwn(user, "name"));console.log(Object.hasOwn(user, "toString"));2. Получение прототипа объекта
Для получения непосредственного прототипа используйте:
Object.getPrototypeOf(object)Пример:
const user = { name: "Иван",};
console.log(Object.getPrototypeOf(user));3. Создание объекта с заданным прототипом
const userPrototype = { showInfo() { console.log(`Пользователь: ${this.name}`); },};
const user = Object.create(userPrototype);
user.name = "Анна";user.showInfo();Метод showInfo() не является собственным свойством user, но доступен через его прототип.
4. Поиск свойства по цепочке прототипов
При обращении:
object.propertyJavaScript:
- ищет свойство в самом объекте;
- если его нет — в прототипе;
- затем в прототипе прототипа;
- поиск заканчивается на
null.
Схематично:
object ↓prototype ↓Object.prototype ↓null5. Переопределение унаследованного свойства
const prototype = { role: "user",};
const admin = Object.create(prototype);
console.log(admin.role); // user
admin.role = "admin";
console.log(admin.role); // adminПри присваивании создаётся собственное свойство объекта. Прототип при этом не изменяется.
6. Функция-конструктор
До появления синтаксиса class объекты одного типа часто создавались через функции-конструкторы.
function User(name, age) { this.name = name; this.age = age;}
const user1 = new User("Иван", 20);const user2 = new User("Анна", 19);При использовании new создаётся новый объект, а его прототип связывается с:
User.prototypeПроверка:
console.log( Object.getPrototypeOf(user1) === User.prototype);7. Общие методы через prototype
Не следует создавать одинаковую функцию отдельно в каждом экземпляре:
function User(name) { this.name = name;
this.showInfo = function () { console.log(this.name); };}Предпочтительнее разместить общий метод в прототипе:
function User(name) { this.name = name;}
User.prototype.showInfo = function () { console.log(this.name);};Тогда экземпляры используют один общий метод.
8. Прототипное наследование функций-конструкторов
Базовый конструктор:
function User(name) { this.name = name;}
User.prototype.showInfo = function () { console.log(this.name);};Производный конструктор:
function Admin(name, permissions) { User.call(this, name);
this.permissions = permissions;}Настройка цепочки прототипов:
Admin.prototype = Object.create(User.prototype);Admin.prototype.constructor = Admin;Новый метод:
Admin.prototype.showPermissions = function () { console.log(this.permissions);};9. Переопределение метода
Admin.prototype.showInfo = function () { console.log(`Администратор: ${this.name}`);};Теперь экземпляр Admin использует собственную реализацию метода, найденную раньше по цепочке прототипов.
10. Связь с дальнейшим class
Синтаксис class, который будет использоваться в следующей практической работе, не отменяет прототипы.
Даже объект, созданный через класс, продолжает использовать цепочку прототипов.
Поэтому задача этой практической работы — понять механизм, на котором построена объектная модель JavaScript.
Задания для выполнения
Section titled “Задания для выполнения”Часть 1. Исследование прототипной модели
Выполните задания 1–4 полностью.
Задание 1.1. Собственные и унаследованные свойства
Создайте:
const user = { name: "Иван", age: 20,};Выведите результаты:
Object.hasOwn(user, "name")Object.hasOwn(user, "toString")"name" in user"toString" in userОбъясните различие между Object.hasOwn() и оператором in.
Задание 1.2. Создание объекта через Object.create()
Создайте прототип:
const accountPrototype = { showInfo() { alert( `Логин: ${this.login}\n` + `Активен: ${this.active}` ); },};Создайте два объекта через Object.create(accountPrototype).
Добавьте им собственные свойства:
loginactiveВызовите showInfo() для каждого.
Проверьте:
Object.getPrototypeOf(account1) === accountPrototypeЗадание 1.3. Переопределение метода
Добавьте в прототип:
getAccessLevel()который возвращает строку:
Обычный доступДля одного объекта создайте собственный метод getAccessLevel(), возвращающий:
Расширенный доступПроверьте оба объекта и объясните, почему результат различается.
Задание 1.4. Функция-конструктор
Создайте:
function Product(id, name, price) { this.id = id; this.name = name; this.price = price;}Добавьте через Product.prototype методы:
showInfo()changePrice(newPrice)Создайте минимум три товара и сохраните их в массив.
Проверьте:
Object.getPrototypeOf(products[0]) === Product.prototypeЧасть 2. Комплексное индивидуальное задание
Section titled “Часть 2. Комплексное индивидуальное задание”Вариант 1. Пользователи и администраторы
Создайте функции-конструкторы:
UserAdminUser:
idnameactiveМетоды:
showInfo()activate()deactivate()Admin наследуется от User и дополнительно содержит:
permissionsДобавьте метод:
showPermissions()Переопределите showInfo().
Программа должна позволять показать пользователей, найти пользователя по id, изменить активность и вывести администраторов.
Вариант 2. Устройства и сетевые устройства
Создайте:
DeviceNetworkDeviceDevice:
idnameonlineМетоды:
showInfo()turnOn()turnOff()NetworkDevice дополнительно:
ipМетод:
changeIp()Переопределите showInfo() так, чтобы отображался IP-адрес.
Вариант 3. Транспорт и автомобили
Создайте:
VehicleCarVehicle:
idbrandspeedМетоды:
showInfo()accelerate(value)stop()Car дополнительно:
fuelДобавьте:
refuel(amount)Переопределите showInfo().
Не допускайте отрицательную скорость и количество топлива.
Вариант 4. Персонажи и воины
Создайте:
CharacterWarriorCharacter:
namehealthlevelМетоды:
showInfo()takeDamage(value)heal(value)Warrior дополнительно:
armorДобавьте метод:
takeDamage()с переопределённой логикой: броня уменьшает получаемый урон.
Вариант 5. Товары и цифровые товары
Создайте:
ProductDigitalProductProduct:
idnamepriceМетоды:
showInfo()changePrice()DigitalProduct дополнительно:
fileSizedownloadLinkПереопределите showInfo() и добавьте:
getDownloadInfo()Вариант 6. Заявки и инциденты
Создайте:
TicketIncidentTicket:
idtitlestatusМетоды:
showInfo()changeStatus()Incident дополнительно:
priorityДобавьте:
isCritical()Переопределите showInfo().
Вариант 7. Банковские счета и премиальные счета
Создайте:
AccountPremiumAccountAccount:
idownerbalanceМетоды:
showInfo()deposit()withdraw()PremiumAccount дополнительно:
cashbackPercentДобавьте:
calculateCashback(amount)Переопределите showInfo().
Не допускайте списание суммы больше баланса.
Вариант 8. Сотрудники и руководители
Создайте:
EmployeeManagerEmployee:
idnamesalaryМетоды:
showInfo()changeSalary()Manager дополнительно:
departmentbonusДобавьте:
calculateTotalIncome()Переопределите showInfo().
Вариант 9. Медиафайлы и видео
Создайте:
MediaFileVideoFileMediaFile:
idnamesizeМетоды:
showInfo()rename()VideoFile дополнительно:
durationresolutionДобавьте:
getVideoInfo()Переопределите showInfo().
Вариант 10. Бронирования и VIP-бронирования
Создайте:
BookingVipBookingBooking:
idguestpriceМетоды:
showInfo()changePrice()VipBooking дополнительно:
discountserviceДобавьте:
calculateFinalPrice()Переопределите showInfo().
Требования к результату
Section titled “Требования к результату”Программа должна:
- использовать прототипную модель без
class; - содержать минимум две связанные функции-конструктора;
- хранить общие методы в
prototype; - иметь корректно настроенную цепочку прототипов;
- использовать массив экземпляров;
- содержать поиск и изменение данных;
- содержать хотя бы одно переопределение метода;
- использовать интерактивный ввод;
- обрабатывать ошибочный ввод;
- демонстрировать результаты
Object.getPrototypeOf().
Что предоставить преподавателю
Section titled “Что предоставить преподавателю”- исходный код JavaScript;
- выполненную общую часть;
- комплексный вариант;
- демонстрацию работы программы;
- вывод проверки цепочки прототипов;
- объяснение, какие свойства являются собственными, а какие методы — унаследованными.
Контрольные вопросы
Section titled “Контрольные вопросы”- Что такое прототип объекта?
- Что представляет собой цепочка прототипов?
- Как получить прототип объекта?
- Для чего используется
Object.create()? - Чем собственное свойство отличается от унаследованного?
- Для чего используется
Object.hasOwn()? - Чем
Object.hasOwn()отличается от оператораin? - Где JavaScript ищет свойство, отсутствующее в объекте?
- Что происходит при создании собственного свойства с тем же именем, что и у прототипа?
- Что такое функция-конструктор?
- Для чего используется оператор
new? - Что хранится в свойстве
prototypeфункции-конструктора? - Почему общие методы лучше хранить в
prototype? - Как проверить связь экземпляра с
Constructor.prototype? - Для чего используется
call()при наследовании? - Зачем после
Object.create()восстанавливать свойствоconstructor? - Что называется переопределением метода?
- Почему
classв JavaScript не отменяет прототипы? - Почему
__proto__не рекомендуется использовать в прикладном коде? - Как связаны экземпляр,
Constructor.prototypeиObject.prototype?