Polymorphism ในภาษา PHP

20 January 2017

ในการเขียนโปรแกรมเชิงวัตถุ (Object-Oriented Programming) Polymorphism เป็นคุณสมบัติพื้นฐานที่สำคัญในการแอพพลิชันให้มีความหลากหลายในการใช้งาน โดยการแชร์รูปแบบการทำงานที่เหมือนกัน ในบทนี้ เราจะพูดถึงแนวคิดทั่วไปของ Polymorphism รวมถึงวิธีและตัวอย่างของการนำไปประยุกต์ใช้งานในภาษา PHP

Polymorphism คืออะไร

Polymorphism คือการกำหนดวิธีการทำงานที่แตกต่างกันให้กับคลาสในการเขียนโปรแกรมเชิงวัตถุ โดยที่คลาสนั้นมีการใช้ Interfaces พื้นฐานร่วมกัน สิ่งสำคัญในการใช้ Polymorphism คือการทำงานของโปรแกรมกับคลาสต่างๆ นั้นไม่จำเป็นต้องทราบถึงวิธีการทำงานที่แต่ละคลาสทำ แต่สิ่งที่เราตระหนักถึงคือการใช้งานคลาสเหล่านั้น คำว่า Polymorphism นั้นเป็นคำในภาษากรีกซึ่งมีความหมายว่า หลากหลาย หรือหลายรูปแบบ

Polymorphism in OOP, PHP programming

ตัวอย่างของ Polymorphism ให้คุณมีคลาสของรูปหลายเหลี่ยม เช่น รูปสามเหลียม และรูปสี่เหลี่ยม ถึงแม้มันจะเป็นคลาสคนละอย่างกันแต่มันอยู่ในหมวดหมู่เดียวกัน คือรูปทรง ดังนั้นเราจึงได้มีการกำหนด Interfaces สำหรับคลาสเหล่านี้ และทำการ Implement Interfaces สำหรับการทำงานของรูปทรงแต่ละแบบ นี่เป็นความหมายของ Polymorphism

Abstract class Polymorphism

Polymorphism จึงทำงานร่วมกันกับ Interfaces หรือ Abstract class ซึ่งสิ่งเหล่านี้เป็นสิ่งกำหนดและการที่คลาสสามารถนำไปใช้ร่วมกันได้ ต่อไปมาดูตัวอย่างในการประยุกต์ใช้แนวคิดของ Polymorphism ในภาษา PHP

<?php

abstract class Shape {

    protected $x;
        protected $y;

    public function __construct($x, $y) {
        $this->x = $x;
        $this->y = $y;
    }

    public abstract function draw();
    public abstract function area(); 

}

class Triangle extends Shape {

    public function draw() {
        for ($i = 0; $i < $this->y; $i++) {
            $inner = $this->x * $i / $this->y + 1;
            for ($j = 0; $j < $inner; $j++) {
                echo "*";
            }
            echo "\n";
        }
    }

    public function area() {
        return $this->x * $this->y / 2;
    }

}

class Rectangle extends Shape {

    public function draw() {
        for ($i = 0; $i < $this->y; $i++) {
            for ($j = 0; $j < $this->x; $j++) {
                echo "*";
            }
            echo "\n";
        }
    }

    public function area() {
        return $this->x * $this->y;
    }
}

$shapes = [ new Triangle(6, 6), new Rectangle(6, 6), 
            new Triangle(6, 3), new Rectangle(5, 3) ];

foreach ($shapes as $shape) {
    $shape->draw();
    echo $shape->area() . "\n\n";
}

?>

ในตัวอย่างเราได้สร้างคลาส Shape ซึ่งเป็น abstract class คลาสนี้มีตัวแปร $x และ $y สำหรับเก็บความยาวและความสูงของรูปทรง และเราได้ประกาศ abstract เมธอดสำหรับวาดรูปทรงเหล่านี้ และเมธอดในการหาพื้นที่ของรูปทรง

ต่อมาเราสร้างคลาส Triangle ซึ่งเป็นคลาสของรูปสามเหลี่ยมตรีโกณมิติ และคลาส Rectangle ซึ่งเป็นรูปสี่เหลี่ยมมุมฉาก ซึ่งทั้งสองคลาสนี้สามารถใช้ตัวแปรร่วมกันได้ และเราได้กำหนดการทำงานในเมธอด draw() และเมธอด area() ตามวัตถุประสงค์ของแต่ละคลาส

$shapes = [ new Triangle(6, 6), new Rectangle(6, 6), 
            new Triangle(6, 3), new Rectangle(5, 3) ];

foreach ($shapes as $shape) {
    $shape->draw();
    echo $shape->area() . "\n\n";
}

เราได้สร้างออบเจ็คจากคลาสเหล่านี้เก็บไว้ในอาเรย์ และใช้คำสั่ง foreach loop ในการทำงาน เมื่อเราเรียกใช้เมธอด draw() และเมธอด area() ในตัวแปร $shape เราไม่จำเป็นต้องสนใจว่าเมธอดของคลาสไหนจะถูกเรียก Polymorphism จะทำการเรียกใช้เมธอดของออบเจ็คให้อัตโนมัติ ทำให้โปรแกรมของเรามีความยืดหยุ่น เช่น คุณอาจจะต้องการเพิ่มรูปร่างอื่นเข้ามา

*
**
***
****
*****
******
18

******
******
******
******
******
******
36

*
***
*****
9

*****
*****
*****
15

และนี่เป็นผลลัพธ์การทำงานของ Polymorphism เมื่อเรารันโปรแกรม

Interfaces Polymorphism

ในตัวอย่างก่อนหน้านั้นเป็นการใช้งาน Polymorphism กับ Abstract class ต่อไปเป็นตัวอย่างการใช้งานกับ Interfaces ซึ่งมีวิธีการที่คล้ายกันแต่เราเปลี่ยนจากการสืบทอดมาเป็น Implements แทน เราจะสร้างคลาสของสัตว์ที่มีการใช้งาน Interfaces ร่วมกัน

<?php

interface iAnimal {

    public function move();
    public function sleepPlace(); 

}

class Dog implements iAnimal {

    public function move() {
        echo "Dog is running\n";
    }

    public function sleepPlace() {
        echo "Dog sleeps in house\n";
    }

}

class Fish implements iAnimal {

    public function move() {
        echo "Fish is swimming\n";
    }

    public function sleepPlace() {
        echo "Fish sleeps in water\n";
    }

}

class Bird implements iAnimal {

    public function move() {
        echo "Bird is flying\n";
    }

    public function sleepPlace() {
        echo "Bird sleeps in tree\n";
    }

}

$animals = [ new Dog(), new Fish(), new Bird() ];

foreach ($animals as $animal) {
    $animal->move();
    $animal->sleepPlace();
}

?>

ในตัวอย่างเป็นการใช้ Interfaces ในการทำงานแบบ Polymorphism เราได้สร้าง Interfaces iAnimal ซึ่งเป็น Interfaces สำหรับกำหนดฟังก์ชันการเคลื่อนไหว และบอกสถานที่นอนของสัตว์ ซึ่ง Interfaces นี้ถูกนำไป Implements ด้วย 3 คลาสคือ Dog Fish และ ฺBird ซึ่งเป็นคลาสของสุนัข ปลา และนกตามลำดับ แต่ละคลาสได้มีการกำหนดการทำงานสำหรับเมธอดเคลื่อนไหว และที่พักอาศัยแตกต่างกันออกไป

Dog is running
Dog sleeps in house
Fish is swimming
Fish sleeps in water
Bird is flying
Bird sleeps in tree

นี่เป็นผลลัพธ์การทำงานของโปรแกรม คุณจะเห็นได้ว่าการทำงานของออบเจ็คจากคลาสต่างๆ นั้นแตกต่างกันจากการใช้เมธอดเดียวกัน นี่เป็นเพราะว่าเกิดจากการ Implements Interfaces

ในบทนี้ เราได้อธิบายถึงแนวคิดของ Polymorphism และการนำไปประยุกต์ใช้ในการเขียนโปรแกรมร่วมกับ Interfaces และ Abstract class ในภาษา PHP Polymorphism เป็นสิ่งหนึ่งที่ช่วยให้คุณสามารถจัดการการเขียนโปรแกรมใน OOP ที่ซับซ้อนให้ยืดหยุ่นได้ในหลายรูปแบบของคลาส ที่สามารถควบคุมได้ในวิธีเดียวกันแต่ทำงานแตกต่างกัน

บทความนี้เป็นประโยชน์หรือไม่?Yes·No