PHP
Python

Trang chủ

OOP trong Python là gì? Tổng quan về OOP trong Python

Ngôn ngữ Python là một ngôn ngữ lập trình đa mục đích, nổi tiếng với cú pháp dễ đọc, dễ học và tính ứng dụng cao. Trong lĩnh vực phát triển web, Python thường được sử dụng thông qua các framework như Django và Flask để xây dựng các ứng dụng web mạnh mẽ, bảo mật và dễ mở rộng. Trong chuyên mục này, Vietnix không chỉ cung cấp kiến thức nền tảng về ngôn ngữ Python mà còn hướng dẫn chi tiết cách xây dựng các ứng dụng web thực tế, sử dụng các framework phổ biến và áp dụng các kỹ thuật tiên tiến. Vietnix cam kết liên tục cập nhật những bài viết mới nhất về các tính năng mới của Python, các thư viện hỗ trợ hữu ích và những phương pháp tốt nhất, giúp bạn khai thác tối đa sức mạnh của Python và hoàn thiện kỹ năng lập trình web của mình.
html
CSS
javascript
sql
python
php
c
c++
bootstrap
react
mysql
reactjs
vuejs
Javascript Tutorials
08/03/2025
19 phút đọc
Theo dõi Vietnix trên

OOP trong Python là gì? Tổng quan về OOP trong Python

Lập trình hướng đối tượng (OOP) trong Python là một mô hình lập trình dựa trên việc tổ chức mã nguồn thành các đối tượng, bao gồm thuộc tính (dữ liệu) và phương thức (hành vi). Phương pháp này giúp code dễ quản lý, tái sử dụng và mở rộng hơn, đặc biệt hữu ích cho các dự án lớn. Trong bài viết này, mình sẽ trình bày chi tiết về OOP trong Python, từ khái niệm cơ bản đến các kỹ thuật nâng cao.

Những điểm chính

  • Phương pháp tiếp cận theo hướng thủ tục: Hiểu cách lập trình truyền thống hoạt động và lý do OOP trở thành lựa chọn tối ưu hơn trong nhiều trường hợp.
  • Khái niệm OOP trong Python: Biết được cách tổ chức mã nguồn theo hướng đối tượng, với hai yếu tố chính là thuộc tính (dữ liệu) và hành vi (phương thức).
  • Class và Object trong OOP: Nắm rõ cách khai báo lớp (class) và tạo đối tượng (object) để xây dựng các chương trình linh hoạt, dễ bảo trì.
  • Encapsulation – Đóng gói: Hiểu cách kiểm soát truy cập dữ liệu trong lớp, đảm bảo tính bảo mật và ngăn chặn thay đổi ngoài ý muốn.
  • Inheritance – Kế thừa: Biết cách mở rộng chức năng của lớp cha mà không cần viết lại toàn bộ mã nguồn, giúp tiết kiệm thời gian và công sức.
  • Polymorphism – Đa hình: Hiểu cách một phương thức có thể hoạt động linh hoạt trên nhiều đối tượng khác nhau, giúp mã nguồn linh động hơn.
  • Vietnix – Nhà cung cấp dịch vụ lưu trữ uy tín, chất lượng: Tìm hiểu về các giải pháp hosting và VPS tại Vietnix, đảm bảo hiệu suất cao và hỗ trợ tối ưu cho lập trình viên.
  • Câu hỏi thường gặp: Giải đáp các thắc mắc về encapsulation, phương thức thay thế kế thừa, cách sử dụng @property và mô phỏng interface trong Python.

Phương pháp tiếp cận theo hướng thủ tục

Lập trình theo hướng thủ tục (Procedural Programming) là mô hình lập trình phổ biến trong những năm 50-60, khi các chương trình được xây dựng dựa trên chuỗi các lệnh tuần tự để thực hiện một nhiệm vụ cụ thể. Mô hình này chia chương trình thành các hàm (function) độc lập, giúp tái sử dụng mã nguồn và tổ chức logic tốt hơn. Các hàm trong lập trình thủ tục có thể giao tiếp với nhau thông qua đối số (arguments) và giá trị trả về. Điều này giúp chương trình có tính linh hoạt cao, dễ dàng thực thi từng phần mà không cần chạy toàn bộ mã nguồn.

Phương pháp tiếp cận theo hướng thủ tục
Phương pháp tiếp cận theo hướng thủ tục

Hạn chế của lập trình theo hướng thủ tục

  • Khó bảo trì: Do cách tiếp cận từ trên xuống (top-down), khi chương trình lớn dần, việc thay đổi hoặc mở rộng sẽ rất khó khăn.
  • Quản lý dữ liệu kém: Sử dụng quá nhiều biến toàn cục (global variables) khiến chương trình dễ xảy ra lỗi và tiêu tốn bộ nhớ không cần thiết.
  • Không tách biệt dữ liệu và xử lý: Mô hình này ưu tiên xử lý (process) mà không quan tâm nhiều đến việc bảo vệ dữ liệu, dẫn đến dữ liệu có thể bị thay đổi bất cứ lúc nào trong chương trình.
  • Dữ liệu di chuyển tự do: Không có cơ chế kiểm soát chặt chẽ dữ liệu giữa các hàm, điều này gây khó khăn trong những tình huống thực tế, nơi dữ liệu cần được gắn liền với một thực thể cụ thể.

Giả sử, trong một hệ thống quản lý khách hàng của Vietnix, nếu lập trình theo hướng thủ tục, tất cả thông tin khách hàng sẽ được lưu trữ trong các biến toàn cục. Khi cần cập nhật hoặc truy xuất dữ liệu, các hàm sẽ trực tiếp truy cập vào những biến này. Điều này có thể dẫn đến lỗi hoặc sự thay đổi dữ liệu ngoài ý muốn, làm giảm tính bảo mật và khó bảo trì về lâu dài. Chính vì những hạn chế này, lập trình theo hướng đối tượng (OOP) ra đời để giải quyết vấn đề bằng cách gắn dữ liệu với thực thể cụ thể, giúp quản lý chương trình hiệu quả hơn.

OOP trong Python là gì?

OOP (Object-Oriented Programming) là một mô hình lập trình hướng đối tượng, trong đó chương trình được xây dựng dựa trên các đối tượng – đại diện cho các thực thể trong thế giới thực với thuộc tính (dữ liệu) và hành vi (phương thức). Python là một trong những ngôn ngữ lập trình hỗ trợ mạnh mẽ lập trình hướng đối tượng, giúp lập trình viên dễ dàng xây dựng và quản lý các ứng dụng phức tạp.

OOP trong Python là một mô hình lập trình hướng đối tượng
OOP trong Python là một mô hình lập trình hướng đối tượng

Đối tượng trong thế giới thực và lập trình hướng đối tượng

Trong thực tế, bạn làm việc với nhiều đối tượng khác nhau, chẳng hạn như khách hàng, hóa đơn, máy chủ, dịch vụ hosting,… Mỗi đối tượng đều có thuộc tínhhành vi riêng:

Thuộc tính

Thuộc tính (Attribute): Là các thông tin mô tả đối tượng. Ví dụ:

  • Một khách hàng có tên, email, số điện thoại.
  • Một hóa đơn có mã số, danh sách sản phẩm, tổng tiền.
  • Một gói dịch vụ hosting có tên gói, dung lượng lưu trữ, băng thông.

Hành vi

Hành vi (Behavior): Là những thao tác mà đối tượng có thể thực hiện. Ví dụ:

  • Khách hàng có thể đăng ký dịch vụ, gia hạn hosting.
  • Hóa đơn có thể tính tổng tiền, áp dụng mã giảm giá.
  • Gói hosting có thể tính mức sử dụng tài nguyên, tự động gia hạn.

Nguyên tắc của OOP

Lập trình hướng đối tượng trong Python dựa trên bốn nguyên tắc chính:

  • Lớp (Class) và Đối tượng (Object) – Cấu trúc nền tảng của OOP.
  • Đóng gói (Encapsulation) – Giúp bảo vệ dữ liệu, chỉ cho phép truy cập thông qua các phương thức được định nghĩa trước.
  • Kế thừa (Inheritance) – Cho phép một lớp mở rộng chức năng từ lớp khác mà không cần viết lại mã nguồn.
  • Đa hình (Polymorphism) – Giúp một phương thức hoạt động linh hoạt trên nhiều đối tượng khác nhau.

Class và Object trong OOP

Trong lập trình hướng đối tượng (OOP), class (lớp) là một khuôn mẫu do người dùng định nghĩa, dùng để tạo ra các object (đối tượng). Một class bao gồm thuộc tính (biến lớp và biến đối tượng) và phương thức (hàm hoạt động trên dữ liệu của lớp). Các đối tượng được tạo ra từ class sẽ kế thừa tất cả các đặc điểm của class đó.

Class và Object trong OOP
Class và Object trong OOP

Dưới đây là ví dụ về cách khai báo class và tạo object trong Python, trong đó mô phỏng một dịch vụ lưu trữ:

# Định nghĩa class
class HostingPlan:
    # Constructor    
    def __init__(self, plan_name, storage):
        self.plan_name = plan_name
        self.storage = storage
    # Phương thức của class
    def description(self):
        return f"Gói {self.plan_name} cung cấp {self.storage} dung lượng, tối ưu cho website tốc độ cao."
# Tạo object từ class
planObj = HostingPlan("Vietnix NVMe Hosting", "100GB SSD")
print(planObj.description())
  • Kết quả như sau:

Gói Vietnix NVMe Hosting cung cấp 100GB SSD dung lượng, tối ưu cho website tốc độ cao.

Giải thích:

    • Class HostingPlan mô phỏng một gói hosting với các thuộc tính như tên gói (plan_name) và dung lượng lưu trữ (storage).

    • Phương thức description() giúp mô tả gói hosting.

    • Object planObj là một instance của class HostingPlan, đại diện cho một gói hosting cụ thể tại Vietnix.

Encapsulation – Đóng gói

Encapsulation (đóng gói) là một trong những nguyên tắc quan trọng của lập trình hướng đối tượng (OOP). Nó giúp bảo vệ dữ liệu của một đối tượng bằng cách giới hạn quyền truy cập từ bên ngoài. Cụ thể, các thuộc tính (data members) của lớp chỉ có thể được truy cập và xử lý bởi các phương thức (methods) bên trong lớp đó. Điều này đảm bảo rằng dữ liệu của đối tượng không bị thay đổi một cách không kiểm soát từ bên ngoài.

Bằng cách sử dụng các thuộc tính có phạm vi truy cập riêng tư (private), encapsulation giúp:

  • Bảo mật dữ liệu: Ngăn chặn truy cập trái phép từ bên ngoài.
  • Kiểm soát dữ liệu: Chỉ cho phép chỉnh sửa dữ liệu thông qua các phương thức cụ thể, đảm bảo tính nhất quán.
  • Dễ dàng bảo trì và mở rộng: Khi cần thay đổi logic xử lý dữ liệu, bạn chỉ cần sửa đổi các phương thức mà không ảnh hưởng đến phần còn lại của chương trình.

Giả sử, bạn có một hệ thống quản lý gói dịch vụ lưu trữ. Một gói dịch vụ có giá trị tài nguyên nhất định, nhưng không thể bị thay đổi trực tiếp từ bên ngoài mà phải thông qua phương thức được định sẵn:

class HostingPlan:
    def __init__(self):
        self.__max_bandwidth = 100  # Đơn vị: GB
    def show_bandwidth(self):
        return f"Băng thông tối đa: {self.__max_bandwidth}GB"
    def upgrade_bandwidth(self, new_bandwidth):
        if new_bandwidth > self.__max_bandwidth:
            self.__max_bandwidth = new_bandwidth
# Khởi tạo đối tượng
plan = HostingPlan()
print(plan.show_bandwidth())
# Thử thay đổi băng thông trực tiếp (không có tác dụng)
plan.__max_bandwidth = 200
print(plan.show_bandwidth())
# Nâng cấp băng thông đúng cách thông qua setter
plan.upgrade_bandwidth(200)
print(plan.show_bandwidth())
  • Kết quả như sau:

Băng thông tối đa: 100GB

Băng thông tối đa: 100GB

Băng thông tối đa: 200GB

Trong ví dụ trên, thuộc tính max_bandwidth được khai báo là private, do đó không thể thay đổi trực tiếp từ bên ngoài. Việc cập nhật băng thông chỉ có thể thực hiện thông qua phương thức upgrade_bandwidth(), đảm bảo dữ liệu được kiểm soát và không bị sửa đổi ngoài ý muốn. Encapsulation giúp hệ thống hoạt động ổn định, tránh lỗi do truy cập dữ liệu không hợp lệ, đồng thời giúp quản lý dịch vụ dễ dàng hơn.

Inheritance – Kế thừa

Kế thừa (Inheritance) trong lập trình hướng đối tượng (OOP) cho phép một lớp (class) mới mở rộng khả năng của một lớp đã có sẵn thay vì xây dựng từ đầu. Lớp gốc (base class hay parent class) chứa các thuộc tính và phương thức có thể được tái sử dụng, trong khi lớp con (subclass hay child class) kế thừa và có thể mở rộng hoặc tùy chỉnh lại những tính năng này.

Lợi ích của kế thừa

  • Tái sử dụng mã nguồn: Giúp tiết kiệm thời gian bằng cách sử dụng lại các phương thức và thuộc tính có sẵn.
  • Dễ dàng mở rộng: Lớp con có thể thêm tính năng mới hoặc sửa đổi hành vi của lớp cha mà không làm ảnh hưởng đến các phần khác của chương trình.
  • Cấu trúc rõ ràng: Giúp tổ chức mã nguồn tốt hơn, hỗ trợ bảo trì và mở rộng trong tương lai.

Cú pháp 

Lớp con được khai báo bằng cách đặt tên lớp cha trong dấu ngoặc sau tên lớp con:

class SubClassName(ParentClass):
    'Chuỗi tài liệu tùy chọn'
    class_suite

Ví dụ

Giả sử Vietnix đang phát triển một hệ thống quản lý khách hàng cho dịch vụ hosting. Bạn có một lớp Customer đại diện cho khách hàng chung và một lớp VIPCustomer kế thừa từ Customer, mở rộng thêm các tính năng đặc biệt dành cho khách hàng VIP.

# Định nghĩa lớp cha
class Customer:
    def __init__(self, name, email):
        self.name = name
        self.email = email
    def show_info(self):
        print(f"Tên khách hàng: {self.name}")
        print(f"Email: {self.email}")
# Định nghĩa lớp con kế thừa từ Customer
class VIPCustomer(Customer):
    def __init__(self, name, email, support_level):
        super().__init__(name, email)
        self.support_level = support_level
    def show_vip_info(self):
        self.show_info()
        print(f"Cấp độ hỗ trợ: {self.support_level}")
# Tạo đối tượng từ lớp con
vip = VIPCustomer("Nguyễn Văn A", "nguyenvana@example.com", "Hỗ trợ ưu tiên")
vip.show_vip_info()
  • Kết quả như sau:

Tên khách hàng: Nguyễn Văn A

Email: nguyenvana@example.com

Cấp độ hỗ trợ: Hỗ trợ ưu tiên

Kiểm tra mối quan hệ kế thừa: Python cung cấp hai hàm hữu ích để kiểm tra mối quan hệ giữa các lớp và đối tượng:

  • issubclass(sub, sup): Trả về True nếu sub là lớp con của sup.
  • isinstance(obj, Class): Trả về True nếu obj là một thể hiện của Class hoặc một lớp con của Class.

Ví dụ:

print(issubclass(VIPCustomer, Customer))  # True
print(isinstance(vip, Customer))  # True
print(isinstance(vip, VIPCustomer))  # True

Polymorphism – Đa hình

Polymorphism (đa hình) trong lập trình hướng đối tượng là khả năng một phương thức có thể có nhiều cách triển khai khác nhau tùy vào lớp con. Điều này giúp mã nguồn linh hoạt hơn, cho phép thay đổi hành vi của phương thức mà không cần chỉnh sửa trực tiếp lớp cha.

Ví dụ

Trong Python, các lớp con có thể ghi đè (override) phương thức của lớp cha để cung cấp cách hoạt động riêng phù hợp với từng tình huống cụ thể. Ví dụ, trong hệ thống quản lý dịch vụ tại Vietnix, các gói hosting có thể có phương thức hiển thị thông tin khác nhau tùy vào loại hình dịch vụ:

# Định nghĩa lớp cha
class Hosting:
    def service_info(self):
        print("Dịch vụ lưu trữ tại Vietnix")
# Định nghĩa lớp con với cách triển khai riêng
class VPSHosting(Hosting):
    def service_info(self):
        print("Dịch vụ VPS của Vietnix với hiệu suất cao")
class SharedHosting(Hosting):
    def service_info(self):
        print("Dịch vụ Shared Hosting của Vietnix, tiết kiệm và tối ưu")
# Tạo đối tượng từ lớp con
service1 = VPSHosting()
service2 = SharedHosting()
# Gọi phương thức đã ghi đè
service1.service_info()  # Output: Dịch vụ VPS của Vietnix với hiệu suất cao
service2.service_info()  # Output: Dịch vụ Shared Hosting của Vietnix, tiết kiệm và tối ưu

Phương pháp nạp chồng cơ sở trong Python

Python cho phép nạp chồng (overload) một số phương thức đặc biệt để thay đổi cách hoạt động mặc định của một đối tượng. Dưới đây là một số phương thức thường được nạp chồng:

Phương thứcMô tảVí dụ sử dụng
__init__(self, [...])Constructor, khởi tạo đối tượng với tham sốobj = MyClass(args)
__del__(self)Destructor, giải phóng bộ nhớ khi đối tượng bị xóadel obj
__repr__(self)Trả về chuỗi biểu diễn có thể đánh giá được của đối tượngrepr(obj)
__str__(self)Trả về chuỗi hiển thị của đối tượngstr(obj)
__cmp__(self, x)So sánh hai đối tượngcmp(obj1, obj2)

Quá tải toán tử trong Python

Python hỗ trợ quá tải toán tử (operator overloading), cho phép định nghĩa lại cách các toán tử hoạt động trên các đối tượng tự định nghĩa. Ví dụ, trong hệ thống quản lý tài nguyên của Vietnix, bạn có thể định nghĩa phép cộng giữa hai gói tài nguyên:

class Resource:
    def __init__(self, cpu, ram):
        self.cpu = cpu
        self.ram = ram
    def __str__(self):
        return f"Resource(CPU: {self.cpu} vCPUs, RAM: {self.ram} GB)"
    def __add__(self, other):
        return Resource(self.cpu + other.cpu, self.ram + other.ram)
# Khởi tạo hai gói tài nguyên
r1 = Resource(2, 4)
r2 = Resource(4, 8)
# Cộng hai gói tài nguyên
print(r1 + r2)  # Output: Resource(CPU: 6 vCPUs, RAM: 12 GB)

Với cách tiếp cận này, các đối tượng trong hệ thống có thể hoạt động một cách linh hoạt hơn, cải thiện khả năng tái sử dụng và bảo trì mã nguồn.

Vietnix – Nhà cung cấp dịch vụ lưu trữ uy tín, chất lượng

Vietnix tự hào là một trong những đơn vị hàng đầu trong lĩnh vực web hosting, cung cấp hạ tầng máy chủ mạnh mẽ cùng hệ thống backup tự động, đảm bảo dữ liệu luôn an toàn. Với danh mục dịch vụ đa dạng như Hosting Giá Rẻ, Business HostingWordPress HostingSEO Hosting và MaxSpeed Hosting, Vietnix mang đến giải pháp tối ưu cho cả cá nhân và doanh nghiệp. Ngoài ra, Vietnix còn cung cấp VPS chất lượng cao, giúp bạn linh hoạt hơn trong việc quản lý và vận hành hệ thống. Trải nghiệm dịch vụ hosting chuyên nghiệp ngay hôm nay cùng Vietnix!

Thông tin liên hệ:

  • Hotline: 18001093
  • Email: sales@vietnix.com.vn 
  • Địa chỉ: 265 Hồng Lạc, Phường 10, Quận Tân Bình, Thành Phố Hồ Chí Minh.
  • Website: https://vietnix.vn/

Câu hỏi thường gặp

Có cách nào để mô phỏng tính đóng gói (encapsulation) mạnh mẽ hơn trong Python không, khi Python không có từ khóa private như Java?

Python không có từ khóa private như Java, nhưng có thể mô phỏng tính đóng gói bằng:
Name Mangling (__var) – Tránh truy cập ngoài ý muốn.
@property & setter – Kiểm soát quyền truy cập.
weakref – Hạn chế truy cập trực tiếp.
Thư viện accesscontrol – Kiểm soát truy cập nâng cao.

Trong Python, có thể thay đổi hành vi của một lớp mà không cần kế thừa hoặc sửa đổi trực tiếp lớp đó không?

Có, trong Python có thể thay đổi hành vi của một lớp mà không cần kế thừa hoặc chỉnh sửa trực tiếp bằng cách:
Monkey Patching – Gán lại phương thức của lớp tại runtime.
Decorator – Bọc quanh phương thức để thay đổi hành vi.
Metaclass – Tùy chỉnh cách tạo lớp.
Duck Typing – Thay thế đối tượng bằng một đối tượng có hành vi tương tự.

Có nên sử dụng @property thay vì các phương thức getter và setter truyền thống trong Python không?

Có, nên sử dụng @property thay vì getter và setter truyền thống trong Python vì:
Cú pháp ngắn gọn, dễ đọc – Truy cập như một thuộc tính thay vì gọi phương thức.
Kiểm soát truy cập linh hoạt – Có thể thêm logic mà không thay đổi cách sử dụng.
Đảm bảo tính đóng gói – Tránh việc truy cập trực tiếp vào biến nội bộ.
Tuy nhiên, nếu cần xử lý phức tạp hoặc có nhiều tham số, phương thức getter/setter vẫn có thể phù hợp hơn.

Tại sao Python không có từ khóa interface như Java và làm sao để mô phỏng behavior tương tự?

Python không có từ khóa interface như Java vì:
Python là ngôn ngữ linh hoạt, không bắt buộc kiểu dữ liệu chặt chẽ – Dựa trên duck typing (nếu một đối tượng có phương thức phù hợp, nó có thể được sử dụng).
Dùng Abstract Base Class (ABC) – Python hỗ trợ mô phỏng interface thông qua abc.ABC và @abstractmethod.
Protocol từ Python 3.8+ – Cho phép định nghĩa behavior mà không cần kế thừa, tương tự interface.
Có thể mô phỏng interface bằng cách sử dụng ABC hoặc Protocol tùy theo nhu cầu.

Lời kết

OOP trong Python (lập trình hướng đối tượng) cung cấp một cách tiếp cận mạnh mẽ để xây dựng và quản lý mã nguồn hiệu quả. Với các yếu tố cốt lõi như lớp (class), đối tượng (object), kế thừa (inheritance) và đa hình (polymorphism), OOP giúp tổ chức code tốt hơn, dễ bảo trì và mở rộng. Việc nắm vững OOP không chỉ giúp bạn viết code Python chuyên nghiệp hơn mà còn mở ra cơ hội làm việc với các dự án lớn, từ phát triển ứng dụng đến trí tuệ nhân tạo. Nếu bạn chưa quen với OOP, hãy thực hành viết các lớp và đối tượng để làm chủ kỹ thuật này!

Cao Lê Viết Tiến

PHP Leader
tại
Vietnix

Kết nối với mình qua

Icon Quote
Icon Quote

Học lập trình online cùng vietnix

Học lập trình online cùng Vietnix

PHPXem thêmThu gọn