Chi tiết bài học Hàm bạn (friend function)

Hàm bạn (friend function)

Trong bài này, bạn sẽ được học cách tạo hàm bạn và lớp bạn trong C + +, và cách sử dụng chúng hiệu suất cao trong chương trình của bạn .

Một trong những định nghĩa quan trọng của OOP là che giấu dữ liệu, nghĩa là hàm không phải thành viên sẽ không thể truy xuất dữ liệu private hoặc protected của một đối tượng.

Nhưng, đôi lúc sự số lượng giới hạn này sẽ khiến lập trình viên phải viết đoạn mã nguồn dài và phức tạp. Vì thế, có một chính sách dựng sẵn trong lập trình C + + được cho phép truy xuất tài liệu private hoặc protected từ những hàm không phải thành viên .
Điều này được thực thi trải qua hàm bạn hoặc lớp bạn .

Hàm bạn trong C++

Một hàm được định nghĩa là hàm bạn sẽ hoàn toàn có thể truy xuất tài liệu private và protected của một lớp .

Trình biên dịch sẽ biết một hàm là hàm bạn thông qua từ khóa friend.

Để truy xuất tài liệu, lời khai báo hàm bạn nên được đặt bên trong thân của lớp ( hoàn toàn có thể nằm ở bất kể đâu bên trong lớp, dù ở khu vực private hay public ) khởi đầu với từ khóa friend .

Khai báo hàm bạn trong C++

class class_name
{
    ... .. ...
    friend return_type function_name(argument/s);
    ... .. ...
}

Giờ bạn hoàn toàn có thể định nghĩa hàm bạn như một hàm thường thì để truy xuất tài liệu của lớp. Không có từ khóa friend được sử dụng khi định nghĩa hàm .

class className
{
    ... .. ...
    friend return_type functionName(argument/s);
    ... .. ...
}

return_type functionName(argument/s)
{
    ... .. ...
    // dữ liệu private và protected của lớp className có thể
    // được truy xuất bởi hàm này vì nó là hàm bạn của lớp className.
    ... .. ...
}

Ví dụ 1: Cách hoạt động của hàm bạn

/* Chương trình C++ mô tả hoạt động của hàm bạn.*/
#include 
using namespace std;

class Distance
{
    private:
        int meter;
    public:
        Distance(): meter(0) { }
        //hàm bạn
        friend int addFive(Distance);
};

// định nghĩa hàm bạn
int addFive(Distance d)
{
    //truy xuất dữ liệu private từ hàm không phải thành viên
    d.meter += 5;
    return d.meter;
}

int main()
{
    Distance D;
    cout<<"Distance: "<< addFive(D);
    return 0;
}

Đầu ra

Distance : 5

Ở đây, hàm bạn addFive() được khai báo trong lớp Distance. Vì thế, dữ liệu private meter có thể được truy xuất từ hàm này.

Mặc dù ví dụ này đưa ra sáng tạo độc đáo về định nghĩa hàm bạn, nhưng nó không chỉ ra bấy kỳ ý nghĩa sử dụng nào .
Một cách sử dụng có ý nghĩa hơn đó là khi bạn cần thao tác trên những đối tượng người dùng của hai lớp khác nhau. Đó là khi hàm bạn hoàn toàn có thể thực sự hữu dụng .
Bạn trọn vẹn có thể thao tác trên hai đối tượng người dùng của những lớp khác nhau mà không cần sử dụng hàm bạn, nhưng chương trình sẽ trở nên dài, phức tạp và khó hiểu .

Ví dụ 2: Cộng các thành viên của hai lớp khác nhau sử dụng hàm bạn

#include 
using namespace std;

// khai báo trước
class B;
class A {
    private:
      int numA;
    public:
      A(): numA(12) { }
      // khai báo hàm bạn
      friend int add(A, B);
};

class B {
    private:
       int numB;
    public:
       B(): numB(1) { }
       // khai báo hàm bạn
       friend int add(A, B);
};

// hàm add() là hàm bạn của lớp A và B
// có thể truy xuất biến thành viên numA và numB
int add(A objectA, B objectB)
{
   return (objectA.numA + objectB.numB);
}

int main()
{
    A objectA;
    B objectB;
    cout<<"Sum: "<< add(objectA, objectB);
    return 0;
}

Đầu ra

Sum : 13

Trong chương trình này, lớp A và B được khai báo add ( ) là một hàm bạn. Vì thế, hàm này hoàn toàn có thể truy xuất tài liệu private của cả hai lớp .
Ở đây, hàm add ( ) sẽ cộng hai biến private numA và numB của hai đối tượng người dùng objectA và objectB, và trả về cho hàm main ( ) .
Để giúp chương trình chạy đúng, một tiền khai báo ( forward delcaration ) của lớp B nên được đưa ra giống như ví dụ trên .
Đó là chính do lớp B được tham chiếu tới trong lớp A ở đoạn mã : friend int add ( A, B ) ; .

Lớp bạn trong lập trình C++

Tương tự, giống như trường hợp hàm bạn, một lớp cũng có thể trở thành bạn của một lớp khác sử dụng từ khóa friend. Ví dụ:

... .. ...
class B;
class A
{
   // lớp B là một lớp bạn của lớp A
   friend class B;
   ... .. ...
}

class B
{
   ... .. ...
}

Khi một lớp trở thành một lớp bạn, mọi hàm thành viên của lớp đó đều trở thành hàm bạn .
Trong chương trình này, mọi hàm thành viên của lớp B sẽ trở thành hàm bạn của lớp A. Vì vậy, bất kể hàm thành viên nào của lớp B cũng hoàn toàn có thể truy xuất vào tài liệu private và protected của lớp A. Nhưng hàm thành viên của lớp A không hề truy xuất tài liệu của lớp B .
Nên nhớ, mối quan hệ bạn trong C + + chỉ mang ý nghĩa được cho phép, không có nghĩa là chiếm đoạt .