2009-02-21 33 views

Trả lời

3

Bạn sẽ sử dụng một hàm bạn bè cho cùng một loại lý do mà bạn sẽ sử dụng một lớp bạn bè, nhưng trên cơ sở thành viên (chứ không phải toàn bộ lớp) cơ sở. Một số giải thích tốt là ở số this thread.

Trong khi chức năng và lớp học của bạn bè vi phạm đóng gói, chúng có thể hữu ích trong một số trường hợp. Ví dụ: bạn có thể muốn cho phép khai thác thử nghiệm truy cập vào nội dung lớp học để cho phép bạn thực hiện kiểm tra whitebox. Thay vì mở toàn bộ lớp học để khai thác thử nghiệm, bạn có thể mở ra một chức năng cụ thể truy cập vào các bộ phận bên trong được yêu cầu bởi dây nịt thử nghiệm. Trong khi điều này vẫn vi phạm đóng gói, nó ít rủi ro hơn việc mở toàn bộ lớp học.

Cũng xem this article để biết thêm thông tin về các lớp và chức năng của bạn bè.

0

Đôi khi mức độ bảo vệ công cộng/riêng tư/bảo vệ không đủ cho các tình huống thực tế. Vì vậy, do đó, chúng tôi đưa ra một mệnh đề nhỏ để giúp đỡ mà không phải làm cho các phương thức có thể truy cập công khai.

Cá nhân tôi sử dụng cách này giống như cách Java sử dụng cấp độ bảo vệ 'Gói'.
Nếu tôi có một lớp học trong cùng một gói cần truy cập, tôi sẽ xem xét sử dụng bạn bè. Nếu nó là một lớp học trong một gói khác thì tôi sẽ tự hỏi tại sao trên trái đất này là lớp khác cần truy cập và nhìn vào thiết kế của tôi.

1

Xem C++ FAQ Lite:

Đôi khi bạn bè là cú pháp tốt hơn (ví dụ, trong lớp Fred, chức năng bạn cho phép tham số Fred là thứ hai, trong khi các thành viên cần nó để là người đầu tiên). Một cách sử dụng tốt các chức năng của bạn là các toán tử số học nhị phân. Ví dụ, aComplex + aComplex nên được định nghĩa là một người bạn chứ không phải là thành viên nếu bạn muốn cho phép aFloat + aComplex (các hàm thành viên không cho phép quảng cáo đối số bên trái, vì điều đó sẽ thay đổi lớp của đối tượng người nhận lời gọi hàm thành viên).

2

Chức năng và lớp học của bạn không vi phạm đóng gói khi bạn đang cố gắng xây dựng một giao diện trừu tượng hoặc phải trải qua nhiều lớp hoặc chức năng C++! Đó là lý do tại sao bạn được phát minh.

Các loại trường hợp này không xuất hiện thường xuyên, nhưng đôi khi bạn buộc phải triển khai một giao diện trừu tượng hoặc giao diện với các lớp và chức năng khác nhau. Ví dụ cổ điển đang triển khai một số loại lớp số phức. Các hàm toán tử không phải là thành viên được cung cấp tình bạn cho lớp số phức chính.

Tôi cũng nhớ khi thực hiện điều này khi lập trình với CORBA trong C++. CORBA buộc tôi phải có các lớp riêng biệt để thực hiện các công chức của Corba. Nhưng đối với một phần cụ thể của phần mềm của chúng tôi, tôi cần kết hôn với nhau như một giao diện. Tình bạn cho phép hai lớp này làm việc cùng nhau để cung cấp một dịch vụ liên tục cho một phần của phần mềm của chúng tôi.

Có khả năng đánh dấu một chức năng thành viên cụ thể trên một lớp khác với tư cách một người bạn trong lớp của bạn có vẻ xa lạ hơn, nhưng đó chỉ là cách kiểm soát chặt chẽ tình bạn. Thay vì cho phép toàn bộ lớp khác "vào" làm bạn của bạn, bạn chỉ cho phép một trong các chức năng truy cập thành viên của nó. Một lần nữa, điều này không phổ biến, nhưng rất hữu ích khi bạn cần.

+1

+1 cho "không vi phạm". Tuy nhiên, nó là vô ích trong trường hợp của hầu hết các lớp số như phức tạp, hợp lý, ... –

0

Một điểm mà tôi thấy có liên quan: các lớp thành viên có quyền truy cập vào các phần riêng tư của lớp chứa. Điều này đôi khi có thể là một lựa chọn tốt hơn cho "người bạn".

class A 
{ 
private: 
    int b; 
public: 
    class MemberNotFriend { 
    public: 
    static void test() { 
     A a; 
     a.b = 0; 
    } 
    }; 


}; 


void test() 
{ 
    A::MemberNotFriend::test(); 
} 
0

Đây là một đơn giản, ví dụ cụ thể về cách tôi đang sử dụng một hàm friend:

Tôi có một trò chơi trong đó mỗi đối tượng sprite lưu trữ thông tin của nó như X, Y vị trí như các thành viên tư nhân. Tuy nhiên, tôi muốn tách các đối tượng trò chơi khỏi hiển thị: đối tượng trò chơi không cần chi tiết chính xác về cách hiển thị. Một đối tượng trò chơi chỉ lưu trữ trạng thái trò chơi và trạng thái trò chơi này có thể được hiển thị theo một số cách khác nhau.

Do đó lớp đối tượng trò chơi có chức năng kết bạn: render(). Hàm render() được thực hiện bên ngoài lớp đối tượng trò chơi, nhưng nó có thể truy cập vào các vị trí bản ghi vị trí vị trí X, Y khi cần để hiển thị đối tượng trò chơi.

Các vấn đề liên quan