+1

PHP và MySQL Bài 9: Các hàm (Functions) - Đóng gói logic và Tái sử dụng mã nguồn

Khi dự án ngày càng lớn, bạn sẽ nhận thấy có những đoạn logic phải sử dụng đi sử dụng lại ở nhiều nơi (ví dụ: định dạng ngày tháng, tính toán giá vé, kiểm tra quyền người dùng). Nếu copy/paste đoạn code đó khắp nơi, khi cần sửa đổi một quy tắc nhỏ, bạn sẽ phải đi tìm và sửa hàng chục file khác nhau – một cơn ác mộng thực sự trong bảo trì hệ thống.

Giải pháp cho vấn đề này là Hàm (Functions). Hàm cho phép bạn đóng gói một đoạn code thực hiện một nhiệm vụ cụ thể thành một "module" độc lập, đặt cho nó một cái tên và có thể gọi ra sử dụng ở bất kỳ đâu.


1. Cách tự định nghĩa và gọi hàm cơ bản

Để tạo một hàm trong PHP, chúng ta sử dụng từ khóa function, theo sau là tên hàm và cặp ngoặc đơn ().

Quy tắc đặt tên hàm: Giống hệt quy tắc đặt tên biến (không bắt đầu bằng số, không chứa khoảng trắng), nhưng thường được viết theo chuẩn camelCase (ví dụ: calculateTotal, getUserInfo).

<?php
    // 1. Định nghĩa hàm
    function sendSystemAlert() {
        echo "[CẢNH BÁO]: Máy chủ trạm đang gặp sự cố kết nối cơ sở dữ liệu!\n";
        // Có thể gọi thêm API gửi tin nhắn qua Telegram/Slack ở đây
    }

    // 2. Gọi hàm (Có thể gọi bao nhiêu lần tùy thích)
    sendSystemAlert(); 
    sendSystemAlert();
?>

2. Tham số (Parameters) và Đối số (Arguments)

Một hàm sẽ linh hoạt hơn rất nhiều nếu nó có thể nhận dữ liệu đầu vào để xử lý. Dữ liệu đầu vào này được gọi là Tham số.

<?php
    // $hoTen và $vaiTro là Tham số (Parameters) - đóng vai trò như biến cục bộ trong hàm
    function createWelcomeMessage($hoTen, $vaiTro) {
        echo "Xin chào " . $hoTen . ", bạn đang đăng nhập với quyền " . $vaiTro . ".\n";
    }

    // Khi gọi hàm, các giá trị truyền vào gọi là Đối số (Arguments)
    createWelcomeMessage("Huy Hoàng", "Quản trị viên");
    createWelcomeMessage("Người dùng A", "Khách");
?>

Giá trị mặc định cho tham số:

Bạn có thể thiết lập giá trị mặc định cho tham số. Nếu khi gọi hàm không truyền đối số, hệ thống sẽ lấy giá trị mặc định này.

<?php
    function connectDatabase($host = "127.0.0.1", $port = 3306) {
        echo "Đang kết nối tới DB tại " . $host . ":" . $port . "\n";
    }

    connectDatabase(); // Output: Đang kết nối tới DB tại 127.0.0.1:3306
    connectDatabase("192.168.1.100"); // Output: Đang kết nối tới DB tại 192.168.1.100:3306
?>

3. Lệnh return - Trả về kết quả

Trong thực tế xây dựng Backend và API, các hàm hiếm khi dùng lệnh echo để in trực tiếp ra màn hình. Thay vào đó, chúng xử lý dữ liệu và trả về (return) kết quả để các phần khác của hệ thống tiếp tục sử dụng.

Khi gặp từ khóa return, hàm sẽ lập tức kết thúc và trả lại giá trị. Mọi dòng code nằm dưới return trong hàm đó sẽ bị bỏ qua.

<?php
    // Hàm tính giá vé sau khi áp dụng mã giảm giá
    function calculateFinalPrice($basePrice, $discountPercent) {
        if ($discountPercent < 0 || $discountPercent > 100) {
            return $basePrice; // Nếu mức giảm giá không hợp lệ, trả về nguyên giá
        }
        
        $discountAmount = $basePrice * ($discountPercent / 100);
        $finalPrice = $basePrice - $discountAmount;
        
        return $finalPrice;
    }

    // Hứng kết quả trả về vào một biến để xử lý tiếp
    $giaVeHocSinh = calculateFinalPrice(15000, 50);
    echo "Giá vé cần thanh toán: " . $giaVeHocSinh . " VNĐ"; 
?>

4. Tham trị (Pass by Value) và Tham chiếu (Pass by Reference)

Đây là một khái niệm nâng cao rất quan trọng để tránh các lỗi thao tác dữ liệu ngoài ý muốn.

  • Truyền tham trị (Mặc định): Hàm sẽ tạo ra một bản sao của biến được truyền vào. Mọi thay đổi bên trong hàm chỉ tác động lên bản sao đó, biến gốc bên ngoài không bị ảnh hưởng.
  • Truyền tham chiếu: Sử dụng dấu & đặt trước tham số. Hàm sẽ can thiệp trực tiếp vào vùng nhớ của biến gốc. Thay đổi bên trong hàm sẽ làm thay đổi biến gốc bên ngoài.
<?php
    // Truyền tham trị (Không có dấu &)
    function addBonusValue($salary) {
        $salary += 500;
    }
    
    $mySalary = 1000;
    addBonusValue($mySalary);
    echo $mySalary . "\n"; // Vẫn in ra 1000. Biến gốc không thay đổi.

    // Truyền tham chiếu (Có dấu &)
    function addBonusReference(&$salary) {
        $salary += 500;
    }
    
    $myRealSalary = 1000;
    addBonusReference($myRealSalary);
    echo $myRealSalary . "\n"; // In ra 1500. Biến gốc đã bị thay đổi trực tiếp!
?>

5. Phạm vi biến (Variable Scope)

Một quy tắc bảo mật vùng nhớ trong PHP: Biến được khai báo ở đâu thì chỉ sống ở đó.

  • Biến cục bộ (Local Scope): Khai báo bên trong một hàm. Chỉ có thể sử dụng bên trong hàm đó.
  • Biến toàn cục (Global Scope): Khai báo bên ngoài hàm. Hàm không thể tự động gọi biến này vào dùng.

Nếu muốn dùng biến toàn cục bên trong một hàm, bạn phải dùng từ khóa global để "xin phép". Tuy nhiên, trong kiến trúc phần mềm hiện đại (Clean Architecture), việc lạm dụng từ khóa global bị coi là một thói quen xấu (bad practice) vì nó làm luồng dữ liệu khó kiểm soát. Giải pháp tối ưu luôn là truyền dữ liệu vào thông qua Tham số.

<?php
    $systemEnv = "production"; // Biến toàn cục

    function checkEnvironment() {
        // echo $systemEnv; // LỖI: Biến không tồn tại trong phạm vi cục bộ
        
        global $systemEnv;  // Gọi biến toàn cục vào
        echo "Môi trường hiện tại: " . $systemEnv;
    }

    checkEnvironment();
?>

All rights reserved

Viblo
Hãy đăng ký một tài khoản Viblo để nhận được nhiều bài viết thú vị hơn.
Đăng kí