OOP không phát minh ra đóng gói và không đồng nghĩa với đóng gói. Nhiều ngôn ngữ OOP không có bộ sửa đổi truy cập kiểu C ++ / Java. Nhiều ngôn ngữ không phải OOP có các kỹ thuật khác nhau có sẵn để cung cấp đóng gói.
Một cách tiếp cận cổ điển để đóng gói là đóng cửa , như được sử dụng trong lập trình chức năng . Điều này cũ hơn đáng kể so với OOP nhưng theo cách tương đương. Ví dụ: trong JavaScript, chúng tôi có thể tạo một đối tượng như thế này:
function Adder(x) {
this.add = function add(y) {
return x + y;
}
}
var plus2 = new Adder(2);
plus2.add(7); //=> 9
plus2
Đối tượng trên không có thành viên nào cho phép truy cập trực tiếp vào x
- nó hoàn toàn được gói gọn. Các add()
phương pháp là một đóng cửa so với x
biến.
Các C ngôn ngữ hỗ trợ một số loại đóng gói thông qua nó tập tin tiêu đề cơ chế, đặc biệt là con trỏ đục kỹ thuật. Trong C, có thể khai báo tên cấu trúc mà không xác định thành viên của nó. Tại thời điểm đó, không có biến nào của loại cấu trúc đó có thể được sử dụng, nhưng chúng ta có thể sử dụng các con trỏ tới cấu trúc đó một cách tự do (vì kích thước của một con trỏ cấu trúc được biết đến tại thời điểm biên dịch). Ví dụ: xem xét tệp tiêu đề này:
#ifndef ADDER_H
#define ADDER_H
typedef struct AdderImpl *Adder;
Adder Adder_new(int x);
void Adder_free(Adder self);
int Adder_add(Adder self, int y);
#endif
Bây giờ chúng ta có thể viết mã sử dụng giao diện Adder này mà không cần truy cập vào các trường của nó, ví dụ:
Adder plus2 = Adder_new(2);
if (!plus2) abort();
printf("%d\n", Adder_add(plus2, 7)); /* => 9 */
Adder_free(plus2);
Và đây sẽ là chi tiết thực hiện được gói gọn:
#include "adder.h"
struct AdderImpl { int x; };
Adder Adder_new(int x) {
Adder self = malloc(sizeof *self);
if (!self) return NULL;
self->x = x;
return self;
}
void Adder_free(Adder self) {
free(self);
}
int Adder_add(Adder self, int y) {
return self->x + y;
}
Ngoài ra còn có lớp ngôn ngữ lập trình mô-đun , tập trung vào các giao diện cấp mô-đun. Gia đình ngôn ngữ ML bao gồm. OCaml bao gồm một cách tiếp cận thú vị cho các mô-đun được gọi là functor . OOP bị lu mờ và phần lớn là lập trình mô-đun, nhưng nhiều lợi thế có chủ đích của OOP là về tính mô đun hơn là hướng đối tượng.
Ngoài ra còn có quan sát rằng các lớp trong các ngôn ngữ OOP như C ++ hoặc Java thường không được sử dụng cho các đối tượng (theo nghĩa các thực thể giải quyết các hoạt động thông qua liên kết động / công văn muộn) mà chỉ dành cho các loại dữ liệu trừu tượng (trong đó chúng tôi xác định giao diện chung ẩn chi tiết thực hiện nội bộ). Bài viết về Tìm hiểu trừu tượng dữ liệu, được xem xét lại (Cook, 2009) thảo luận về sự khác biệt này chi tiết hơn.
Nhưng có, nhiều ngôn ngữ không có cơ chế đóng gói nào. Trong các ngôn ngữ này, các thành viên cấu trúc được để lại công khai. Nhiều nhất, sẽ có một quy ước đặt tên không khuyến khích sử dụng. Ví dụ, tôi nghĩ Pascal không có cơ chế đóng gói hữu ích.