1 / 43

C++ & OOP

C++ & OOP. Classes Syntax and Semantics Object Model Object Based Programming Object Oriented Programming Expertise. J. J. Hou. 2002.07. 田野調查. □ 曾經寫過 程式 □曾經寫過 C 程式 □曾經寫過 C++ 程式 □曾經寫過 C++ classes □ 曾經用過 C++ classes (例如 C++ 標準程式庫) □曾經用過 Application Framework.

ciara
Télécharger la présentation

C++ & OOP

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. C++ & OOP • Classes Syntax and Semantics • Object Model • Object Based Programming • Object Oriented Programming • Expertise J. J. Hou 2002.07

  2. 田野調查 □曾經寫過程式 □曾經寫過 C 程式 □曾經寫過 C++ 程式 □曾經寫過 C++ classes □曾經用過 C++ classes(例如C++ 標準程式庫) □曾經用過 Application Framework J.J.Hou

  3. 本課程四個習題 □ class Fraction □ class String □ Shape hierarchy □ apply STL to your app. J.J.Hou

  4. Bibliography 專家經驗 編程規範(coding standard) C++ 標準程式庫百科全書 C++ 百科全書 C++ 程式語言經典本 J.J.Hou jjhou@ccca.nctu.edu.tw

  5. Bibliography 專門針對classes 語法、語意、物件模型 物件模型 J.J.Hou jjhou@ccca.nctu.edu.tw

  6. Bibliography STL 運用 STL源碼剖析 STL 原理概念 STL 專家經驗 GP 極致 C++ 設計 新思維 J.J.Hou jjhou@ccca.nctu.edu.tw

  7. Bibliography OOD/Design Patterns J.J.Hou jjhou@ccca.nctu.edu.tw

  8. C++ Supported Programming Paradigms • Procedural-based Programming • Abstract data type (ADT) Programming • Object-Oriented Programming • Generic Programming J.J.Hou jjhou@ccca.nctu.edu.tw

  9. C++ Standard Library : headers and “std” #include <string> // for string class #include <iostream> // for cout using namespace std; int main() { string str1("Hello, World!"); cout << str1; // output: Hello, World! } • STL implementations • Microsoft VC6: P.J. Plauger • Inprise C++Builder4: Rogue Wave Software, Inc • GNU C++ egcs-2.91.57 : Silicon Graphics Computer Systems, Inc J.J.Hou jjhou@ccca.nctu.edu.tw

  10. STL components demo ref: C++ Primer 3/e p593 #include <algorithm> #include <functional> #include <vector> #include <iostream> using namespace std; int main() { int ia[ 6 ] = { 27, 210, 12, 47, 109, 83 }; vector<int> vec( ia, ia+6 ); cout << count_if(vec.begin(), vec.end(), not1(bind2nd(less_equal<int>(), 40))); return 0; } iterator container generic algorithm predicate function object function adaptor(negator) function adaptor(binder) J.J.Hou jjhou@ccca.nctu.edu.tw

  11. STL components STL provides a set of C++ container classes and template algorithms designed to work together to produce a wide range of useful functionality. • containers(泛型容器) • In STL, containers are objects that store collections of other objects (STL, p23) • A sequence container holds an ordered collection of elements of a single type. such as vector, list (Primer p249) • An associative container supports efficient query as to the presence and retrieval of an element, such as map, set. • generic algorithms(泛型演算法) • “algorithm” because they implement common operations such as min(), max(), find(), sort(); “generic” because they operate across multiple container types -- not only the vector and list types, but also the build-in array type.(Primer p571) • The container is bound to the generic algorithm operating on it by an iterator pair. (Primer p571) • iterators(泛型指標) • An iterator provides a general method of successively accessing each element within any of the sequential or associative container types (Primer p265) . They generalize C/C++ pointers (STL p3). • function objects • The traditional solution of parameterize the comparison operator is declaring a pointer to function. (Primer p587) • An alternative parameterization strategy to that of a pointer to function is a function object. A function object is a class that overloads thefunction call operator. (Primer p587) • which generalize ordinary C/C++ functions and allow other components to be efficiently adapted to a variety of tasks (STL p3) • adaptors • A component that modifies the interface of another component (containers, iterators, function objects) (STL p40) • allocators • for controlling storage management (STL p3). Every STL container class uses an allocator class to encapsulate information about the memory model the program is using (STL p43).

  12. declaration and definition in C++ Effective C++ Introduction 所謂宣告(declaration),用來將一個 object、function、class 或 template 的 型別名稱(type name)告訴編譯器。宣告式並不帶有細目資訊。下面統統都是宣告: extern int x; // object declaration int numDigits(int number); // function declaration class Clock; // class declaration template<class T> class SmartPointer; // class template declaration 所謂定義(definition),用來將細目資訊提供給編譯器。對 object而言, 定義式是編譯器為它配置記憶體的地點。對 function或 functiontemplate而言, 定義式提供了函式本體(function body)。對 class或 classtemplate而言, 定義式必須列出該class 或 template 的所有 members: int x; // object definition int numDigits(int number) // function definition { ... } class Clock // class definition { ... }; template<class T> class SmartPointer // class template definition { ... }; J.J.Hou jjhou@ccca.nctu.edu.tw

  13. Class declaration and definition class CListItem; // forward declaration class CList { // ... CListItem* m_end; // 由於 m_end 是個指標,編譯器此時 CListItem* m_front; // 尚不需知道 CListItem 的細節。 }; J.J.Hou jjhou@ccca.nctu.edu.tw

  14. Class declaration and definition // complex,複數。根據數學定義,複數擁有實部 real 和虛部 imaginary。 // 本例以 double 表現實部和虛部兩個值。 class Complex // class head { public: Complex(const double& re=0, const double& im=0) : m_real(re), m_imag(im) // member initialization list { } double real() const { return m_real; } double imag() const { return m_imag; } double real(const double& re) { m_real = re; return m_real; } double imag(const double& im) { m_imag = im; return m_imag; } private: double m_real; // real part(實部) double m_imag; // imaginary part(虛部) }; member functions data members J.J.Hou jjhou@ccca.nctu.edu.tw

  15. Using Complex class Complex { … }; // maybe in header int main() { Complex c1(1,2); Complex c2(3,4); Complex c3 = c1 * c2; Complex c4 = c1 + c2; cout << c3 << endl; cout << c4 << endl; cout << c3.conj() << endl; } J.J.Hou jjhou@ccca.nctu.edu.tw

  16. name mangling and extern “C” class Complex { public: double real() const; double real(const double& re); // ... }; VC++ 編譯器為它們編出來的函式名稱 : ?real@Complex@@QBENXZ ?real@Complex@@QAENABN@Z 可由map file 觀察獲得 • function signature • function prototype J.J.Hou jjhou@ccca.nctu.edu.tw

  17. private Q: 如果 member functions 接受同型的 object,它有沒有權力直接存取該 object 的 private members? Complex& Complex::operator+=(const Complex& x) { m_real += x.m_real; // 直接取用參數 x 的 private m_real m_imag += x.m_imag; // 直接取用參數 x 的 private m_imag return *this; } J.J.Hou jjhou@ccca.nctu.edu.tw

  18. friend operator overloading : may be member or non-member // in complex.h class Complex { friend ostream& operator<<(ostream& os, const Complex& r); ... } // in complex.cpp ostream& operator<<(ostream& os, const Complex& x) { os << '(' << x.m_real // 直接取用 m_real << ',' << x.m_imag // 直接取用 m_imag << "i)"; return os; } J.J.Hou jjhou@ccca.nctu.edu.tw

  19. Scope and Lifetime • global(namespace)scope • local scope • file scope • namespace scope • class scope • global object • local (auto) object • heap (dynamic allocated) object • static local object 寫一程式實地驗證 object lifetime (see the ctor’s and dtor’s invocation) J.J.Hou jjhou@ccca.nctu.edu.tw

  20. Big3 補充: Complex(); 是什麼? Complex c1(); // default ctor? Function declaration! Complex c1; // default ctor Complex c2(c1); // copy ctor Complex c3 = c1; // copy ctor c3 = c1; // copy assignment operator c3 = 2; // assignment operator Complex* pc = new Complex(3,4); // heap object delete pc; // dtor J.J.Hou jjhou@ccca.nctu.edu.tw

  21. Big3: ctor, dtor, operator= class Complex { public: explicit // default ctor, single-arguments ctor Complex(const double& re=0, const double& im=0) : m_real(re), m_imag(im) { } Complex(const Complex& x) // copy ctor : m_real(x.m_real), m_imag(x.m_imag) { } Complex& operator=(const Complex& x) // copy assignment operator { m_real = x.m_real; m_imag = x.m_imag; return *this; } ... }; J.J.Hou jjhou@ccca.nctu.edu.tw

  22. Big3 • 編譯器自動合成 default ctor? • composition • inheritance • virtual mechanism • 編譯器自動合成 copy ctor • 組合與繼承情況下的 copy 規則 • 編譯器自動合成 copy assignment operator 特別注意 pointer member J.J.Hou jjhou@ccca.nctu.edu.tw

  23. Big3 class Empty {}; Ref. Effective C++ 2e, p212 class Empty { public: Empty(); // default constructor Empty(const Empty& rhs); // copy constructor ~Empty(); // destructor — 見以下說明 // 以決定它是否為 virtual Empty& operator=(const Empty& rhs); // assignment operator Empty* operator&(); // address-of operators const Empty* operator&() const; }; const Empty e1; // default constructor; // destructor Empty e2(e1); // copy constructor e2 = e1; // assignment operator Empty *pe2 = &e2; // address-of operator (non-const) const Empty *pe1 = &e1;// address-of operator (const) J.J.Hou jjhou@ccca.nctu.edu.tw

  24. pointers and references memory 注意:sizeof(r) == sizeof(x) int x = 0; int& r = x; r is a reference to x int* p = &x; p is a pointer to x int x=0; int* p = &x; int& r = x; // r 是一個 reference to int,令它代表 x。現在 r,x 都是0 int x2=5; r = x2; // reference 不能重新代表其他物體。現在 r,x 都是5 int* pi = 0; // null pointer int& ri = *pi; // ri 是一個 null reference 嗎? Ref. More Effective C++, p10 J.J.Hou jjhou@ccca.nctu.edu.tw

  25. by value v.s. by reference. Complex& Complex::operator+=(constComplex& x) { m_real += x.real(); // m_real += x.m_real; // 可直接取用參數 x 的 private m_real this->m_imag += x.imag(); // 有沒有 this->都一樣 return *this; } Ref. Effective C++, p96 : in the class C, ‘this’ like below: C* const this; // for non-const member function const C* const this; // for const member function 本例既然直接修改了 *this. 是否可以將回傳值設為 void ? Try it! Complex conj(constComplex& x) // 共軛複數 { return Complex(x.real(), -x.imag()); // impel RVO. // i.e. // Complex c(x.real(), -x.imag()); // return c; // local object, so must return by value } J.J.Hou jjhou@ccca.nctu.edu.tw

  26. This Pointer (Hidden) (in somewhere) member functions implementation code class definition data members object size instantiation object size object 1 object 2 object 3 object 4 object 5 serve 根據不同的 this指標,指向不同的 objects 實體 ref: Polymorphism in C++ p37 chap1 J.J.Hou jjhou@ccca.nctu.edu.tw

  27. Secrets of “this” pointer Complex c1(2,3); Complex c2(3,4); cout << c1 += c2; cout << c1.operator+=(c2); operator<<(cout, c1.operator+=(c2)); operator<<(cout, Complex::operator+=(&c1, c2)); Complex& Complex::operator+=(Complex* this, constComplex& x) { this->m_real += x.m_real; this->m_imag += x.imag(); return *this; } J.J.Hou jjhou@ccca.nctu.edu.tw

  28. Secrets of “this” pointer Complex c1(2,3); Complex c2(3,4); cout << c1 += c2; cout << c2 += c1; C1 Complex& Complex::operator+=(Complex* this, const Complex& x) { ... } C2 J.J.Hou jjhou@ccca.nctu.edu.tw

  29. by value v.s. by reference. tips o. 儘量使用 by reference,不要使用 by value o. 不要在函式中傳回 reference to local object(會造成 dangling) o. 不要在函式中傳回 pointer to heap object(會造成 memory leak) o. 不要傳出 data members 的任何權柄(handle) o. 如果一定得 by value,不必拼命嘗試 by reference例如 Complex Complex::conj(const Complex& x);或如Rational Rational::operator*(const Rational& x); J.J.Hou jjhou@ccca.nctu.edu.tw

  30. Constness const 用來修飾 member functions,可以使編譯器協助我們 測定 const objects 和 member functions 之間的互動關係是否合法 const object (data members 不可有任何變動) non-const object (data members 可有變動) const member function (保證不更改 data members) non-const member function (不保證data members不變) const String(“hello world”); String.print(); // 如果當初設計 string::print() 時未指明 const,以上便是經由const object喚起 non-const member function,會出錯。 J.J.Hou jjhou@ccca.nctu.edu.tw

  31. new operator and operator new Complex* pc = new Complex(1,2); 編譯器轉為... Complex *pc; try { void* mem = ::operator new( sizeof(Complex) ); // 配置記憶體 pc = static_cast<Complex*>(mem); // 轉型 pc->Complex::Complex(1,2); // 建構 // 注意:只有編譯器才可以像上面那樣直接呼叫 ctor } catch( std::bad_alloc ) { // operator new 配置記憶體失敗,不執行 constructor。 } 欲直接喚起ctor, 可利用 placement new : new(p) Complex(1,2); J.J.Hou jjhou@ccca.nctu.edu.tw

  32. delete operator and operator delete Complex* pc = new Complex(1,2); ... delete pc; 編譯器轉為... pc->~Complex(); // 先解構 ::operator delete(pc); // 然後釋放記憶體 J.J.Hou jjhou@ccca.nctu.edu.tw

  33. array new and array delete 喚起三次ctor, 但無法給予初值 Complex* pca = new Complex[3]; ... delete[] pca; 喚起三次dtor cookie,記錄 記憶體大小 pa Complex object Complex object Complex object J.J.Hou jjhou@ccca.nctu.edu.tw

  34. inline function. (test) inline void func() { int i, j; } int main() { int i, j; func(); return 0; } inlining inline function 有macro的優點而無其缺點 J.J.Hou jjhou@ccca.nctu.edu.tw

  35. auto_ptr (1) template<class T> class autoPtr { public: // construct/copy/destroy explicit autoPtr(T* p=0) // default ctor : m_ptr(p) { } autoPtr(autoPtr& a) // copy ctor : m_ptr( const_cast<autoPtr&>(a).release() ) { } autoPtr& operator=(autoPtr& rhs) { reset(rhs.release()); return *this; } ~autoPtr() { delete m_ptr; } J.J.Hou jjhou@ccca.nctu.edu.tw

  36. auto_ptr (2) T& operator*() const { return *m_ptr; } T* operator->() const { return m_ptr; } T* get() const { return m_ptr; } T* release() { // 釋放擁有權並傳回被擁有物的位址 T* tmp = m_ptr; m_ptr = 0; return tmp; } void reset(T* p = 0) { // 刪除原先擁有物,重設為擁有 p if (m_ptr != p) { delete m_ptr; m_ptr = p; } } private: T* m_ptr; // dump pointer }; J.J.Hou jjhou@ccca.nctu.edu.tw

  37. auto_ptr , return a pointer to heap object Complex* func3(double d1, double d2) { Complex* pc = new Complex(d1,d2); // heap object // ... return pc; // return a pointer to heap object } { Complex* pc = func3(2, 3); // pc 接獲 a pointer to heap object. cout << *pc << endl; // (2,3i) //delete pc; // 本應 delete。但後面使用 auto_ptr... auto_ptr<Complex> pc_auto; // GCC not support auto_ptr. pc_auto.reset(pc); // VC6 not support reset(). cout << *pc_auto << endl; // (2,3i) // auto_ptr<Complex> pc_auto2 = func3(3,4); // bcb4 error auto_ptr<Complex> pc_auto2(func3(3,4)); // ok in bcb4 and vc6 cout << *pc_auto2 << endl; // (3,4i) } J.J.Hou jjhou@ccca.nctu.edu.tw

  38. CShape CRect CSquare CEllipse CCircle CTriangle Polymorphism in STL iterator CMyDoc list<CShape*> m_myList list<CShape*>::push_back() 可以把一個 CShape*放入 list尾端 ref: Polymorphism in C++ p79 chap1 J.J.Hou jjhou@ccca.nctu.edu.tw

  39. Inheritance and SubObjects CPoint3d object CPoint2d subobject CPoint subobject 處理 CPoint subobject CPoint member functions 4 bytes 8 bytes 處理 CPoint2d subobject (涵蓋 CPoint subobject) 12 bytes CPoint2d member functions CPoint3d member functions 處理 CPoint3d object (涵蓋 CPoint2d subobject 和 CPoint subobject) ref: Polymorphism in C++ p47 chap1 J.J.Hou jjhou@ccca.nctu.edu.tw

  40. class A,B,C with virtual function(s) class A,B,C without virtual function(s) C++ Object Model : Object Layout for Single Inheritance a (ClassA object) a (ClassA object) 8 bytes vptr m_data1 12 bytes m_data1 m_data2 m_data2 b (ClassB object) b (ClassB object) vptr m_data1 ClassA subobject 12 bytes ClassA subobject m_data1 m_data2 16 bytes m_data2 m_data3 A m_data3 c (ClassC object) c (ClassC object) B vptr ClassA::m_data1 ClassB subobject ClassA::m_data1 m_data2 20 bytes ClassB subobject m_data2 m_data3 24 bytes C m_data3 m_data1 m_data1 m_data4 m_data4 ref: Polymorphism in C++ p104 fig2-2 J.J.Hou jjhou@ccca.nctu.edu.tw

  41. C++ Object Model :vptr and vtbl a (ClassA object) functions implementation vptr ClassA’s vtbl 0x409004 0x0063FDEC 0x401ED0 0x00409004 m_data1 0x0063FDF0 ClassA::func1() 0x401F10 0x00409008 m_data2 0x0063FDF4 0 0x0040900C ClassA::func2() ClassB::func2() b (ClassB object) vptr ClassB’s vtbl 0x409014 0x0063FDDC ClassC::func2() 0x401F80 0x00409014 m_data1 0x0063FDE0 0x401F10 0x00409018 m_data2 0x0063FDE4 0 ClassA::vfunc1() 0x0040901C m_data3 0x0063FDE8 ClassA::vfunc2() ClassB::vfunc1() c (ClassC object) vptr ClassC’s vtbl 0x409024 0x0063FDC4 ClassC::vfunc1() 0x401FF0 0x00409024 ClassA::m_data1 0x0063FDC8 0x401F10 0x00409028 m_data2 0x0063FDCC 0 0x0040902C m_data3 0x0063FDD0 m_data1 0x0063FDD4 ref: Polymorphism in C++ p105 fig2-3 m_data4 0x0063FDD8

  42. C++ Object Model : one polymorphic class, one vtbl a1 (ClassA object) vptr 0x409014 0x0063FD70 m_data1 m_data2 a2 (ClassA object) vptr ClassA’s vtbl 0x409014 0x0063FDA0 0x00409014 m_data1 m_data2 a3 (ClassA object) 0x409014 0x0063FD8C vptr m_data1 m_data2 ref: Polymorphism in C++ p108 fig2-4 J.J.Hou jjhou@ccca.nctu.edu.tw

  43. Inheritance vs. Composition Public inheritance models “is-a” private inheritance models “is implemented-in-terms-of” composition models “has-a” Liskov substitution principle : an object of a derived class should be usable wherever an object of its public base class is. J.J.Hou jjhou@ccca.nctu.edu.tw

More Related