nmk

Лекція 4 (2 години). Функції в PHP: вдосконалення коду

План лекції

  1. Концепція функцій та базовий синтаксис користувацьких функцій (function).
  2. Аргументи функцій: необов’язкові параметри (за замовчуванням).
  3. Передача аргументів: за значенням і за посиланням (&).
  4. Повернення результатів (return) та область видимості змінних (Variable Scope і ключове слово global).

Перелік умовних скорочень

Вступ

Зі збільшенням розмірів проєкту писати весь код зверху вниз в одному файлі (відомий як “спагеті-код”) стає неможливо. Якщо ви написали формулу розрахунку податків для одного товару, і вам знадобилося розрахувати новий товар на іншій сторінці сайту – ви стикаєтеся з дублюванням. Функції (Functions) — це іменовані блоки коду, які створені для групування певної математичної, логічної чи строкової операції, “замикають” її в незалежну капсулу та дозволяють викликати тисячі разів із різних місць системи без її фізичного дублювання. Іншими словами: це інструментарій розробника для підтримки принципу DRY.


1. Концепція функцій та базовий синтаксис

Функція складається із трьох складових-концепцій:

Декларація

Декларація починається з ключового слова function, потім — унікальне ім’я та круглі дужки для параметрів. Загальновизнаний стиль іменування функцій у PHP (і JS) — camelCase (Дієслово-Дія, наприклад calculateTax, sendEmail).

<?php
// Оголошуємо
function showGreets() {
    echo "Привіт від користувацької функції!<br>";
}

// Функція нічого не зробить і нічого не виведе, поки ми не викличемо її явно:
showGreets();
showGreets(); // Можемо викликати її багато разів
?>

2. Аргументи функцій: необов’язкові параметри (Default Parameters)

Функції безперечно гарні, але було б погано створювати окрему функцію “Привітай Івана” і окрему “Привітай Олену”. Функція має бути універсальним обчислювачем (як м’ясорубка, якій все одно, яке м’ясо ви в неї кладете). Ці “рецепти”, або вхідні дані для розрахунку, називаються аргументами.

<?php
// Ми вказуємо, що функція ПОВИННА прийняти 1 аргумент: змінну $name
function sayHello($name) {
    echo "Привіт розробнику, {$name}!<br>";
}

// Передаємо в якості "начинки" конкретні дані:
sayHello("Іван");   // На льоту PHP зробить $name = "Іван" всередині функції
sayHello("Анна");
// sayHello();     // А це буде Fatal Error: Uncaught ArgumentCountError!
?>

Параметри за замовчуванням

Коли ми хочемо, щоб аргумент не був обов’язковим і підставляв щось автоматично (якщо користувач його не вказав у виклику), використовують дефолтні значення через =.

<?php
// $role — необов'язковий. За замовчуванням — 'Guest' (Гість).
function displayProfile($name, $role = 'Guest') {
    echo "Користувач: $name. Його Права: $role <br>";
}

displayProfile("Максим", "Admin"); // Покаже "Admin" (ми надали свій 2-й аргумент)
displayProfile("Олексій");         // Згенерує "Guest"
?>

Важливе правило: Обов’язкові аргументи під час декларації пишуться спочатку. Параметри за замовчуванням ВЖЕ пишуться в самому кінці списку дужок ($x, $y, $z = 10), щоб не порушувати порядок логічної передачі.

3. Передача аргументів: за значенням і за посиланням

Це критично важлива концепція пам’яті комп’ютера.

За Значенням (By Value) — Режим за замовчуванням

Коли ми передаємо в PHP нашу змінну як аргумент і функція починає з нею робити маніпуляції (перераховувати, множити на 2) — насправді фізично PHP бере і створює 100% “КОПІЮ” цих даних. Будь-які зміни з її копією всередині function взагалі ніяк не торкнуться оригінальної змінної (що лежить за її межами). Це захищає оригінал!

<?php
function addFive($number) {
    $number += 5; // Усі модифікації відбуваються з "КОПІЄЮ".
}

$salary = 100;
addFive($salary); // Відправляємо копію $salary в функцію
echo $salary;     // Оригінал $salary залишиться 100!!
?>

За Посиланням (By Reference &)

Якщо ж ми хочемо, щоб функція цілеспрямовано модифікувала “саме ТУ фізичну змінну”, яку ми передали — ми ставимо перед аргументом знак Амперсанд &. Тоді PHP передає не копію, а “Покажчик” (Reference) на оригинальну комірку в ОЗП (Оперативній пам’яті). Цей спосіб працює швидше з великими мегабайтними текстами (масивами).

<?php
// Знак амперсанда (&) означає передачу "за посиланням"
function addBonus(&$number) {
    $number += 100; // Це вже не копія. Це пряма зміна "на місці".
}

$balance = 500;
addBonus($balance);
echo $balance; // ОРИГІНАЛ ВЖЕ 600!!
?>

4. Повернення результатів (return) та Область Видимості (Scope)

Функції sayHello() вище нічого не розраховували і не повертали, вони викликали команду виведення у браузер накшталт echo. Проте, якісна функція не повинна малювати HTML або займатися інтерфейсом (порушення відокремлення логіки). Вона має працювати “безшумно”: прийняти цифри, вирахувати податок, і ПОВЕРНУТИ цей результат тому місцю коду (змінній), яка її викликала.

Рядок із ключовим словом return також діє як break у циклах — функція в цю ж мікросекунду повністю завершує свою роботу. Що б ви не написали під return; в цій функції (будь-який інший echo) — воно ніколи не дочитається процесором.

<?php
// Ця функція нічого не друкує на екран! Вона "безшумна" і повертає лише результат обробки.
function calculateTaxes($price, $taxPercent = 20) {
    $total = $price + ($price * ($taxPercent / 100));
    return $total; // Повертаємо математичний результат. Зупинка функції.
}

// Тепер результат виклику функції можна присвоїти в змінні!
$finalPriceMilk = calculateTaxes(40);
$finalPriceLaptop = calculateTaxes(30000, 15);

// А вже потім окремо виводити в HTML або БД.
echo "Ціна ноута з податками становить: " . $finalPriceLaptop;
?>

Область видимості змінних (Variable Scope)

Головний принцип якісно спроєктованих функцій — “Чистота”.

<?php
$siteName = "Wikipedia"; // Глобальна

function logMessage() {
    // В PHP функції на відміну від JavaScript НЕ БАЧАТЬ того, що лежить ззовні.
    // echo $siteName; // FATAL ERROR: Undefined variable $siteName

    // Єдиний спосіб сказати їй: "використай файл ззовні" – ключове слово global
    global $siteName;
    echo "Лог для сайту: " . $siteName;
}
?>

Увага: Використання ключового слова global для “протягування” глобальних налаштувань всередину функцій сьогодні вважається поганою практикою (Anti-pattern). Правильний процес — передавати настройки просто як параметри розрахунків при виклику (тобто, передати як аргумент).


Висновки

  1. Функції існують для інкапсуляції логіки, повторного використання і реалізації принципу DRY (Don’t Repeat Yourself).
  2. Якісна функція має бути універсальною: вона приймає Аргументи замість хардкоду значень, обробляє код локально і обов’язково здійснює процес return [] для повернення результатів виклику своїм “батькам”.
  3. До параметрів можуть бути застосовані значення “За Замовчуванням”, проте їх варто перераховувати наприкінці списку підключення.
  4. Передача “за посиланням” (через амперсанд &) дозволяє функції втручатися в оригінальну змінну поза її межами і змінювати її, що критично впливає на процес розробки та економію пам’яті ПК.
  5. Змінна всередині блоку і змінна, створена ззовні файлу, навіть з однаковою назвою — ізольовані сутності через правила “Глобальної / Локальної області (Scope)”.

Джерела

  1. Користувацькі функції (Документація PHP): https://www.php.net/manual/ru/functions.user-defined.php
  2. Аргументи функції (Документація PHP): https://www.php.net/manual/ru/functions.arguments.php

Запитання для самоперевірки

  1. Поясніть сутність принципу “DRY” і як користувацькі функції в PHP допомагають його досягати (не просто поясніть словами, а наведіть приклад із практики).
  2. Що станеться, якщо спробувати викликати таку функцію createUser() і передати в неї меншу кількість параметрів-аргументів, ніж вимагалося під час декларації, та коли параметрам НЕ задано значень за замовчуванням?
  3. Де і чому необхідно розміщувати ті параметри функції, які містять “Значення За Замовчуванням” (на початку функції, в кінці дужок чи довільно) і чим це обґрунтовано?
  4. Розкажіть різницю та наслідки між передачею “за значенням” (by value, без спеціальних символів) і передачею “за посиланням” (by reference, символ &). Яка передача стоїть у PHP “За Замовчуванням”?
  5. Що таке механізм Області Видимості (Variable Scope)? Поясніть концепцію Локальної пам’яті, що знищується по завершенні оператора return. Чи побачить функція змінну $total, якщо ви оголосили її рядком вище до декларації function calculate(...) без слова global?