面向對象編程是一種程序設計範式,它將真實世界的概念抽象為對象,並通過對象之間的交互來實現程序功能。C++是一種支持面向對象編程的編程語言,其中類和對象是面向對象編程的核心概念。
一、類和對象的概念
類是一種抽象數據類型,它描述了一組具有相同特徵和行為的對象。類定義了對象的屬性和方法。對象是類的一個實例,它具有類定義的所有屬性和方法。例如,人類可以被描述為一個類,而每個人則是這個類的一個對象。
C++中定義類的語法如下:
class className { public: // 屬性和方法 }
其中,className是類的名稱,public表示該類的屬性和方法可以被其他類訪問。
定義類的屬性和方法類似於定義變量和函數:
class Person { public: string name; int age; void sayHello() { cout << "Hello, my name is " << name << ", I'm " << age << " years old." << endl; } };
上面的代碼定義了一個Person類,其中包含了name和age兩個屬性,以及一個sayHello()方法。這個方法用於輸出「Hello, my name is xxx, I’m xxx years old.」。
聲明一個對象的語法為:
className objectName;
其中,className是類名稱,objectName是對象名稱。例如,我們可以聲明一個Person對象:
Person p1;
這個對象p1將具有Person類定義的所有屬性和方法。
二、類的訪問修飾符
C++中,類的訪問修飾符用於控制類的屬性和方法的訪問級別。C++中有三種訪問修飾符,分別是public、private和protected。它們的區別如下:
- public屬性和方法可以被任何類訪問。
- private屬性和方法只能被本類中的方法訪問,不能被其他類訪問。
- protected屬性和方法可以在本類和子類中訪問,但不能在其他類中直接訪問。
下面是示例代碼,演示使用不同的訪問修飾符:
class Person { public: string name; // public屬性 void sayHello() { // public方法 cout << "Hello, my name is " << name << endl; } private: int age; // private屬性 void setAge(int a) {// private方法 age = a; } protected: string address; // protected屬性 }; class Student : public Person { public: void setAddress(string a) { address = a; // 可以訪問父類的protected屬性 } }; int main() { Person p1; p1.name = "Jane"; p1.sayHello(); // p1.age = 20; // 錯誤:不能訪問private屬性 // p1.setAge(20); // 錯誤:不能訪問private方法 Student s1; s1.setAddress("Beijing"); // s1.age = 20; // 錯誤:不能訪問父類的private屬性 // s1.setAge(20); // 錯誤:不能訪問父類的private方法 return 0; }
上面的代碼演示了Person類和Student類的定義,以及訪問修飾符的使用。在Main函數中,我們可以看到,公共屬性和方法可以在任何地方訪問,私有屬性和方法只能在本類中訪問,而受保護屬性和方法可以在本類和子類中訪問。
三、構造函數和析構函數
構造函數和析構函數是面向對象編程中的重要概念,它們分別用於創建和銷毀對象。
構造函數是一個特殊的方法,用於在創建對象時初始化對象的屬性。C++中的構造函數名稱與類名相同,在定義過程中沒有返回值類型,例如:
class Person { public: Person(string n, int a) { // 構造函數 name = n; age = a; } void sayHello() { cout << "Hello, my name is " << name << ", I'm " << age << " years old." << endl; } private: string name; int age; };
上面的代碼定義了一個Person類,其中有一個構造函數,用於在創建Person對象時初始化對象的屬性。構造函數的參數是待初始化的屬性值。
類似的,析構函數也是一個特殊的方法,用於在銷毀對象時釋放對象的資源。C++中的析構函數名稱與類名相同,但在名稱前面加上一個波浪線(~),例如:
class Person { public: Person(string n, int a) { name = n; age = a; } ~Person() { // 析構函數 cout << "Person object is destroyed." << endl; } void sayHello() { cout << "Hello, my name is " << name << ", I'm " << age << " years old." << endl; } private: string name; int age; };
在上面的代碼中,析構函數用於在銷毀Person對象時輸出一條消息。
四、static成員變量和方法
類的static成員變量和方法是屬於整個類而不是某個對象的。static成員變量和方法可以在對象創建之前就存在,因此它們可以在沒有對象的情況下直接訪問。例如:
class Person { public: static int count; // 定義一個靜態成員變量 Person(string n, int a) { name = n; age = a; count++; // 靜態成員變量count加1 } ~Person() { count--; // 靜態成員變量count減1 } static void getCount() { // 定義一個靜態成員方法 cout << "count = " << count << endl; } private: string name; int age; }; int Person::count = 0; // 靜態成員變量需要在類外進行初始化 int main() { Person p1("John", 20); Person::getCount(); // 靜態方法可以通過類名來調用 Person p2("Jane", 22); Person::getCount(); Person p3("Mary", 25); Person::getCount(); return 0; }
上面的代碼演示了如何定義和使用靜態成員變量和方法。在Person類定義中,我們定義了一個靜態成員變量count和一個靜態方法getCount()。在Main函數中,我們創建了三個Person對象,每次創建對象都會使count加1。通過調用靜態方法getCount(),我們可以輸出count的值。
五、繼承
繼承是面向對象編程中的一個重要概念,它可以讓一個類繼承另一個類的屬性和方法,從而避免代碼重複。在C++中使用”:”符號表示繼承關係,例如:
class Student : public Person { // Student類繼承自Person類 public: string school; void study() { cout << name << " is studying in " << school << endl; } }; int main() { Student s1; s1.name = "John"; s1.age = 20; s1.school = "MIT"; s1.sayHello(); s1.study(); return 0; }
在上面的代碼中,我們創建了一個Student類,並讓它繼承自Person類。由於繼承了Person類,Student類可以使用Person類中的屬性和方法。在Main函數中,我們創建一個Student對象s1,並為它設置屬性值。通過調用sayHello()和study()方法,我們可以輸出一些信息。
六、多態
多態是C++中面向對象編程的重要概念,它指的是同一種行為具有多種不同的表現形式。多態性是面向對象程序設計的一個重要的特點,它可以提高程序的靈活性和可維護性。
C++中多態的實現方式有兩種,分別是函數重載和虛函數。
函數重載是指在同一個類中,可以定義多個名稱相同但參數類型和個數不同的函數。例如:
class Calculator { public: int add(int a, int b) { cout << "Addition of two integers: "; return a + b; } float add(float a, float b) { cout << "Addition of two floats: "; return a + b; } }; int main() { Calculator c1; cout << c1.add(3, 5) << endl; // 輸出8 cout << c1.add(3.1f, 5.7f) << endl; // 輸出8.8 return 0; }
在上面的代碼中,我們定義了一個Calculator類,並在其中定義了兩個名稱相同但參數類型和個數不同的add()方法。在Main函數中,我們分別調用兩個add()方法,並輸出計算結果。由於參數類型和個數不同,因此C++可以識別出應該調用哪個add()方法。
虛函數是指在基類中定義一個虛函數,在派生類中可以對該虛函數進行重定義。虛函數的定義方式為,在函數前加上關鍵字virtual,例如:
class Shape { public: virtual float area() { return 0; } virtual float perimeter() { return 0; } }; class Rectangle : public Shape { public: Rectangle(float l, float w) { length = l; width = w; } float area() { return length * width; } float perimeter() { return 2 * (length + width); } private: float length; float width; }; class Circle : public Shape { public: Circle(float r) { radius = r; } float area() { return PI * radius * radius; } float perimeter() { return 2 * PI * radius; } private: float radius; const float PI = 3.1415926; }; int main() { Shape* s1; Rectangle r1(3, 4); Circle c1(2); s1 = &r1; cout << "Rectangle area: " <area() << endl; cout << "Rectangle perimeter: " <perimeter() << endl; s1 = &c1; cout << "Circle area: " <area() << endl; cout << "Circle perimeter: " <perimeter() << endl; return 0; }
在上面的代碼中,我們定義了一個Shape類,並在其中定義了一個虛函數area()和perimeter()。在Rectangle和Circle類中,我們分別對這兩個方法進行了重定義。在Main函數中,我們聲明了一個Shape指針s1,指向一個Rectangle對象r1。然後我們調用了s1的area()和perimeter()方法,由於Shape類中的area()和perimeter()方法是虛函數,在運行時會根據對象的類型調用相應的方法,因此輸出的結果分別是Rectangle類和Circle類中的方法返回值。這就是多態性的體現。
原創文章,作者:小藍,如若轉載,請註明出處:https://www.506064.com/zh-hk/n/311472.html