SlideShare a Scribd company logo
1 of 19
Download to read offline
OOP in C
Virtual Function


              elpam.tw@gmail.com
              elpam@Taiwan, Taipei, 2008
LICENSE
    ●   本投影片授權方式為:
        –   姓名標示─非商業性─相同方式分享 3.0  台灣版
        –   http://creativecommons.org/licenses/by­nc­sa/3.0/tw/




    ●   所有的範例程式皆為 Public Domain




                                           
                                  elpam.tw@gmail.com
About This Slides
    ●   All example was build by 
        –   GCC­4.1.3
        –   GLIB­1.2.10
        –   GMAKE­3.81




                                   
                          elpam.tw@gmail.com
請先覆習一下 Function Pointer 的使用方式




                        
               elpam.tw@gmail.com
Function Pointer

                            /* 2­1.c */
                            typedef void (*FP) ( void );

                            void hello() { printf("hello "); }

                            int main()
                            {
                                 void world() { printf("worldn"); }
      #> ./2­1
                                 FP fp = hello;
     hello world 
                                 fp();
      #>
                                 fp = world;
                                 fp();
                            };
                                  
                        elpam.tw@gmail.com
Function Pointer (cont')
                                  /* 2­2.c */
    ●
        也可以當參數使用                  typedef void (*FP) ( void );

                                  #define ERROR 1

                                  void error_test( FP callback )
                                  {
                                      if( ERROR ){
                                           callback();
                                      }
                                  }

          #> ./2­2                int main()
          error happened          {
          #>                             void error() { printf("error happenedn"); }
                                         error_test( error );
                                  };

                                     
                            elpam.tw@gmail.com
Function Pointer & Structure
                                /* 2­3.c */
                                typedef void (*FP) ( void* );
    ●
        以 Function Pointer      struct A{
                                        int a;               int b;
        的方式實作 Member                    FP  method;
                                };
        Function                void a_real_method( void* p)
                                {
                                        struct A* this = p;
                                        printf("%d,%dn",this­>a,this­>b);
                                }
                                int main()
                                {
           #> ./2­3                     struct A a;
           1,2                          a.a = 1;        a.b = 2;
           #>                           a.method  = a_real_method;
                                        a.method ( &a );
                                };

                                 
                        elpam.tw@gmail.com
Using Previous Slide to Implement Inherit

2­4.c
    ●   方便閱讀,加上一點 ' 命名規則 '
           –   其實是龜毛的 Rule
    ●   PREFIX_init
           –   該物件的 建構子 (Constructor)
    ●   PREFIX_method
           –   該物件的 成員函式 (member function)

                                  
                         elpam.tw@gmail.com
Member Function's Inherit (1)
struct A {                              void A_real_method_a( void* p) {
       int a;                               struct A* this = p;
       FP  method_a;                        printf("this is method_a %dn",this­>a); 
};                                      }
struct B {                              void B_real_method_b( void* p) {
       struct A parent;                     struct B* this = p;
       int b;                               printf("this is method_b %dn",this­>b); 
       FP  method_b;                    }
};
int main()  {                           void a_init( struct A* a)  {
       struct B b;                          a ­> a = 1;
       a_init( &b );                        a ­> method_a = A_real_method_a;
       b_init( &b );                    }
                                        void b_init( struct B* b)  {
         struct A* ap = &b;                 b ­> b = 2;
                                            b ­> method_b = B_real_method_b;
         ap ­> method_a( ap );          }
         b  .  method_b( &b );
};
                                          
                                 elpam.tw@gmail.com
Member Function's Inherit (2)
                                           /* 2­4.c */
                                           int main()
    ●
        Child 如果希望執行 ( 存取 )                {
                                                  struct B b;
        Parent 的函式 ( 變數 ) ,需要                     a_init( &b );   
        先 Cast 成 Parent 再執行 ( 存                   b_init( &b );

        取)                                        struct A* ap = &b;

                                                  ap ­> method_a( ap );
                                                  b  .  method_b( &b );
                                           };



                                             #> ./2­4
                                             this is method_a 1
                                             this is method_b 2

                                             #>
                      elpam.tw@gmail.com
結論
    ●
        我們可以實作 class_init() 時將 class 內的
        member value and member function 都設定好
           –   也就是 ''Constructor'' 
    ●   自已實作 C 不提供的 Member Function!!




                                     
                            elpam.tw@gmail.com
Implement Virtual Function

2­5.c
    ●   Child 的 init 可以將 Parent 的 Member Function
        做改寫的動作,以達到 Virtual Function 的效果
           –   下一頁粉紅色的那一行




                                 
                        elpam.tw@gmail.com
Virtual Function (1)
void A_real_method_a( void* p) 
{
       struct A* this = p;
       printf("this is %s %dn"
                         ,__FUNCTION__,this­>a);          void A_init( struct A* a)
}                                                         {
void B_real_method_a( void* p)                                a ­> a = 1;
{                                                             a ­> method_a = A_real_method_a;
       struct B* this = p;                                }
       printf("this is %s %dn"
                          ,__FUNCTION__,this­>b); 
}                                                         void B_init( struct B* b)
void B_real_method_b( void* p)                            {
{                                                             struct A* a = b;
       struct B* this = p;                                    b ­> b = 2;
       printf("this is %s %dn"                               a ­> method_a = B_real_method_a;
                           ,__FUNCTION__,this­>b);            b ­> method_b = B_real_method_b;
}                                                         }

                                                       
                                             elpam.tw@gmail.com
Virtual Function (2)
    ●
        A_init 一定要比 B_init 先執行
        –   Parent 的 Constructor 需要先執
            行                         /* 2­5.c */
                                                         int main()
                                                         {
                                                              struct B b;
          #> ./2­5                                            A_init( &b );
        this is A_real_method_a 1
        this is B_real_method_a 2                             struct A* ap = &b;
        this is B_real_method_b 2                             ap ­> method_a( ap );
          #>
                                                              B_init( &b );
                                                              ap ­> method_a( ap );
                                                              b  .  method_b( &b );
                                                         };
                                             
                                    elpam.tw@gmail.com
Constructor's Wrapper
            2­6.c




                  
         elpam.tw@gmail.com
Constructor in C (1)
    ●   we use PREFIX_new to replace malloc
        –   所有的物件都以 PREFIX_NEW 產生,以確保
            Constructor 被正確的執行

            struct A{                struct A* A_new()
               int a;                {
               int b;                   struct A* ret = malloc( sizeof(A) );
            };                          ret ­> a = 0;
                                        ret ­> b = 1;
                                        return ret;
                                     }




                                       
                              elpam.tw@gmail.com
Constructor in C (2)
    ●
         以前面的例子


        /* 2­6.c */                                       /* 2­6.c */
        int main()                                        struct B* B_new()
        {                                                 {
                struct B* pb = B_new();                      struct B* pb = malloc( sizeof(B) );
                                                             struct A* pa = pb;
                ((struct A*)pb) ­> method_a( pb );           A_init( pa );
                pb ­> method_b( pb );                        B_init( pb );
                                                             return pb;
        };                                                }



                                                      
                                          elpam.tw@gmail.com
Constructor in C (3)
    ●
        繼承關係越復雜時, PREFIX_new 很難去維護
        –   請試想三層繼承時,開發者希望在第一及第二層之間
            再加上一層物件
    ●
        所以我們需要更有效率的方式來撰寫
        Constructor
        –   GObject 提供了一個有效率的方式




                               
                      elpam.tw@gmail.com
Conclusion
    ●
        以上的 Tips 提供了一種方式來撰寫 Object­
        Oriented 的程式
          –   可自行練習 :)
    ●   相較於 C++ 的繼承,此種方式所撰寫出來的物
        件為靜態形別,所有的 Offset 都是 Compiler 
        Time 已決定好的,所以不會有繼承濫用的問題
          –   執行效率
    ●   但是如果不正確的使用,依舊會造成程式碼難以
 
        閱讀,也容易產生 BUG 
                         elpam.tw@gmail.com

More Related Content

What's hot

竞赛中C++语言拾遗
竞赛中C++语言拾遗竞赛中C++语言拾遗
竞赛中C++语言拾遗乐群 陈
 
C語言 第一章 C語言簡介
C語言 第一章 C語言簡介C語言 第一章 C語言簡介
C語言 第一章 C語言簡介shademoon
 
Lua 语言介绍
Lua 语言介绍Lua 语言介绍
Lua 语言介绍gowell
 
Java 開發者的函數式程式設計
Java 開發者的函數式程式設計Java 開發者的函數式程式設計
Java 開發者的函數式程式設計Justin Lin
 
Scala function-and-closures
Scala function-and-closuresScala function-and-closures
Scala function-and-closureswang hongjiang
 
C語言 第4章 基本輸出與輸入功能
C語言 第4章 基本輸出與輸入功能C語言 第4章 基本輸出與輸入功能
C語言 第4章 基本輸出與輸入功能shademoon
 
lambda/closure – JavaScript、Python、Scala 到 Java SE 7
lambda/closure – JavaScript、Python、Scala 到 Java SE 7lambda/closure – JavaScript、Python、Scala 到 Java SE 7
lambda/closure – JavaScript、Python、Scala 到 Java SE 7Justin Lin
 
10 檔案說明與處理
10 檔案說明與處理10 檔案說明與處理
10 檔案說明與處理shademoon
 
Introduction to Basic Haskell Components (In Chinese)
Introduction to Basic Haskell Components (In Chinese)Introduction to Basic Haskell Components (In Chinese)
Introduction to Basic Haskell Components (In Chinese)ChengHui Weng
 
07 陣列與字串
07 陣列與字串07 陣列與字串
07 陣列與字串shademoon
 
Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫
Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫
Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫Justin Lin
 

What's hot (20)

竞赛中C++语言拾遗
竞赛中C++语言拾遗竞赛中C++语言拾遗
竞赛中C++语言拾遗
 
Python 迴圈作業
Python 迴圈作業Python 迴圈作業
Python 迴圈作業
 
Python變數與資料運算
Python變數與資料運算Python變數與資料運算
Python變數與資料運算
 
C語言 第一章 C語言簡介
C語言 第一章 C語言簡介C語言 第一章 C語言簡介
C語言 第一章 C語言簡介
 
Lua 语言介绍
Lua 语言介绍Lua 语言介绍
Lua 语言介绍
 
Java 開發者的函數式程式設計
Java 開發者的函數式程式設計Java 開發者的函數式程式設計
Java 開發者的函數式程式設計
 
Scala function-and-closures
Scala function-and-closuresScala function-and-closures
Scala function-and-closures
 
functional-scala
functional-scalafunctional-scala
functional-scala
 
C語言 第4章 基本輸出與輸入功能
C語言 第4章 基本輸出與輸入功能C語言 第4章 基本輸出與輸入功能
C語言 第4章 基本輸出與輸入功能
 
lambda/closure – JavaScript、Python、Scala 到 Java SE 7
lambda/closure – JavaScript、Python、Scala 到 Java SE 7lambda/closure – JavaScript、Python、Scala 到 Java SE 7
lambda/closure – JavaScript、Python、Scala 到 Java SE 7
 
Ch08
Ch08Ch08
Ch08
 
10 檔案說明與處理
10 檔案說明與處理10 檔案說明與處理
10 檔案說明與處理
 
Python分支作業
Python分支作業Python分支作業
Python分支作業
 
Python基本資料運算
Python基本資料運算Python基本資料運算
Python基本資料運算
 
C語言應用前置處理
C語言應用前置處理C語言應用前置處理
C語言應用前置處理
 
Ch07
Ch07Ch07
Ch07
 
Introduction to Basic Haskell Components (In Chinese)
Introduction to Basic Haskell Components (In Chinese)Introduction to Basic Haskell Components (In Chinese)
Introduction to Basic Haskell Components (In Chinese)
 
Python程式設計 - 串列資料應用
Python程式設計 - 串列資料應用 Python程式設計 - 串列資料應用
Python程式設計 - 串列資料應用
 
07 陣列與字串
07 陣列與字串07 陣列與字串
07 陣列與字串
 
Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫
Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫
Java SE 8 的 Lambda 連鎖效應 - 語法、風格與程式庫
 

Viewers also liked

Lec 42.43 - virtual.functions
Lec 42.43 - virtual.functionsLec 42.43 - virtual.functions
Lec 42.43 - virtual.functionsPrincess Sam
 
Virtual function
Virtual functionVirtual function
Virtual functionharman kaur
 
Lecture 7, c++(complete reference,herbet sheidt)chapter-17.
Lecture 7, c++(complete reference,herbet sheidt)chapter-17.Lecture 7, c++(complete reference,herbet sheidt)chapter-17.
Lecture 7, c++(complete reference,herbet sheidt)chapter-17.Abu Saleh
 
pointers,virtual functions and polymorphism
pointers,virtual functions and polymorphismpointers,virtual functions and polymorphism
pointers,virtual functions and polymorphismrattaj
 
[OOP - Lec 19] Static Member Functions
[OOP - Lec 19] Static Member Functions[OOP - Lec 19] Static Member Functions
[OOP - Lec 19] Static Member FunctionsMuhammad Hammad Waseem
 
Inheritance, friend function, virtual function, polymorphism
Inheritance, friend function, virtual function, polymorphismInheritance, friend function, virtual function, polymorphism
Inheritance, friend function, virtual function, polymorphismJawad Khan
 
Object Oriented Programming Using C++
Object Oriented Programming Using C++Object Oriented Programming Using C++
Object Oriented Programming Using C++Muhammad Waqas
 
Templates in C++
Templates in C++Templates in C++
Templates in C++Tech_MX
 
pointers, virtual functions and polymorphisms in c++ || in cpp
pointers, virtual functions and polymorphisms in c++ || in cpppointers, virtual functions and polymorphisms in c++ || in cpp
pointers, virtual functions and polymorphisms in c++ || in cppgourav kottawar
 
Abstract Base Class and Polymorphism in C++
Abstract Base Class and Polymorphism in C++Abstract Base Class and Polymorphism in C++
Abstract Base Class and Polymorphism in C++Liju Thomas
 
State of the Word 2011
State of the Word 2011State of the Word 2011
State of the Word 2011photomatt
 

Viewers also liked (17)

16 virtual function
16 virtual function16 virtual function
16 virtual function
 
07. Virtual Functions
07. Virtual Functions07. Virtual Functions
07. Virtual Functions
 
Lec 42.43 - virtual.functions
Lec 42.43 - virtual.functionsLec 42.43 - virtual.functions
Lec 42.43 - virtual.functions
 
Virtual function
Virtual functionVirtual function
Virtual function
 
Lecture 7, c++(complete reference,herbet sheidt)chapter-17.
Lecture 7, c++(complete reference,herbet sheidt)chapter-17.Lecture 7, c++(complete reference,herbet sheidt)chapter-17.
Lecture 7, c++(complete reference,herbet sheidt)chapter-17.
 
pointers,virtual functions and polymorphism
pointers,virtual functions and polymorphismpointers,virtual functions and polymorphism
pointers,virtual functions and polymorphism
 
Roots of polynomials
Roots of polynomialsRoots of polynomials
Roots of polynomials
 
Es272 ch3b
Es272 ch3bEs272 ch3b
Es272 ch3b
 
[OOP - Lec 18] Static Data Member
[OOP - Lec 18] Static Data Member[OOP - Lec 18] Static Data Member
[OOP - Lec 18] Static Data Member
 
Es272 ch3a
Es272 ch3aEs272 ch3a
Es272 ch3a
 
[OOP - Lec 19] Static Member Functions
[OOP - Lec 19] Static Member Functions[OOP - Lec 19] Static Member Functions
[OOP - Lec 19] Static Member Functions
 
Inheritance, friend function, virtual function, polymorphism
Inheritance, friend function, virtual function, polymorphismInheritance, friend function, virtual function, polymorphism
Inheritance, friend function, virtual function, polymorphism
 
Object Oriented Programming Using C++
Object Oriented Programming Using C++Object Oriented Programming Using C++
Object Oriented Programming Using C++
 
Templates in C++
Templates in C++Templates in C++
Templates in C++
 
pointers, virtual functions and polymorphisms in c++ || in cpp
pointers, virtual functions and polymorphisms in c++ || in cpppointers, virtual functions and polymorphisms in c++ || in cpp
pointers, virtual functions and polymorphisms in c++ || in cpp
 
Abstract Base Class and Polymorphism in C++
Abstract Base Class and Polymorphism in C++Abstract Base Class and Polymorphism in C++
Abstract Base Class and Polymorphism in C++
 
State of the Word 2011
State of the Word 2011State of the Word 2011
State of the Word 2011
 

Similar to OOP in C - Virtual Function (Chinese Version)

張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版
張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版
張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版逸 張
 
Chapter 6 point (c)
Chapter 6 point (c)Chapter 6 point (c)
Chapter 6 point (c)hhliu
 
Metro Style Apps from C++ Developers' View
Metro Style Apps from C++ Developers' ViewMetro Style Apps from C++ Developers' View
Metro Style Apps from C++ Developers' ViewEric ShangKuan
 
C++11综述/新特性描述/Overview of C++11 New Features
C++11综述/新特性描述/Overview of C++11 New FeaturesC++11综述/新特性描述/Overview of C++11 New Features
C++11综述/新特性描述/Overview of C++11 New FeaturesPeien Luo
 
改善程序设计技术的50个有效做法
改善程序设计技术的50个有效做法改善程序设计技术的50个有效做法
改善程序设计技术的50个有效做法crasysatan
 
Objc under the_hood_2013
Objc under the_hood_2013Objc under the_hood_2013
Objc under the_hood_2013Michael Pan
 
淺談C#物件導向與DesignPattern.pdf
淺談C#物件導向與DesignPattern.pdf淺談C#物件導向與DesignPattern.pdf
淺談C#物件導向與DesignPattern.pdfBrian Chou 周家禾
 
PHPUnit + Xdebug 单元测试技术
PHPUnit + Xdebug 单元测试技术PHPUnit + Xdebug 单元测试技术
PHPUnit + Xdebug 单元测试技术hoopchina
 
Ian 20151002 es2015
Ian 20151002 es2015Ian 20151002 es2015
Ian 20151002 es2015LearningTech
 
由一个简单的程序谈起--之四
由一个简单的程序谈起--之四由一个简单的程序谈起--之四
由一个简单的程序谈起--之四yiditushe
 
C程式-函式與巨集
C程式-函式與巨集C程式-函式與巨集
C程式-函式與巨集艾鍗科技
 
5, initialization & cleanup
5, initialization & cleanup5, initialization & cleanup
5, initialization & cleanupted-xu
 
Ghost cat 以皮肤为主体的ui框架(唐翎)
Ghost cat 以皮肤为主体的ui框架(唐翎)Ghost cat 以皮肤为主体的ui框架(唐翎)
Ghost cat 以皮肤为主体的ui框架(唐翎)FLASH开发者交流会
 
Js的国(转载)
Js的国(转载)Js的国(转载)
Js的国(转载)Leo Hui
 
Javascript Training
Javascript TrainingJavascript Training
Javascript Trainingbeijing.josh
 
由一个简单的程序谈起――之三(精华)
由一个简单的程序谈起――之三(精华)由一个简单的程序谈起――之三(精华)
由一个简单的程序谈起――之三(精华)yiditushe
 
JavaScript 快速複習 2017Q1
JavaScript 快速複習 2017Q1JavaScript 快速複習 2017Q1
JavaScript 快速複習 2017Q1Sheng-Han Su
 
從 Singleton 談 constructor
從 Singleton 談 constructor從 Singleton 談 constructor
從 Singleton 談 constructorLuba Tang
 
GTest交流与经验总结
GTest交流与经验总结GTest交流与经验总结
GTest交流与经验总结coderzh
 

Similar to OOP in C - Virtual Function (Chinese Version) (20)

張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版
張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版
張逸 - 研究所 / 轉學考計算機概論 、公職計算機概要 - 程式語言 - 試閱版
 
Chapter 6 point (c)
Chapter 6 point (c)Chapter 6 point (c)
Chapter 6 point (c)
 
Metro Style Apps from C++ Developers' View
Metro Style Apps from C++ Developers' ViewMetro Style Apps from C++ Developers' View
Metro Style Apps from C++ Developers' View
 
C++11综述/新特性描述/Overview of C++11 New Features
C++11综述/新特性描述/Overview of C++11 New FeaturesC++11综述/新特性描述/Overview of C++11 New Features
C++11综述/新特性描述/Overview of C++11 New Features
 
改善程序设计技术的50个有效做法
改善程序设计技术的50个有效做法改善程序设计技术的50个有效做法
改善程序设计技术的50个有效做法
 
Objc under the_hood_2013
Objc under the_hood_2013Objc under the_hood_2013
Objc under the_hood_2013
 
淺談C#物件導向與DesignPattern.pdf
淺談C#物件導向與DesignPattern.pdf淺談C#物件導向與DesignPattern.pdf
淺談C#物件導向與DesignPattern.pdf
 
PHPUnit + Xdebug 单元测试技术
PHPUnit + Xdebug 单元测试技术PHPUnit + Xdebug 单元测试技术
PHPUnit + Xdebug 单元测试技术
 
Ian 20151002 es2015
Ian 20151002 es2015Ian 20151002 es2015
Ian 20151002 es2015
 
由一个简单的程序谈起--之四
由一个简单的程序谈起--之四由一个简单的程序谈起--之四
由一个简单的程序谈起--之四
 
C程式-函式與巨集
C程式-函式與巨集C程式-函式與巨集
C程式-函式與巨集
 
5, initialization & cleanup
5, initialization & cleanup5, initialization & cleanup
5, initialization & cleanup
 
Ghost cat 以皮肤为主体的ui框架(唐翎)
Ghost cat 以皮肤为主体的ui框架(唐翎)Ghost cat 以皮肤为主体的ui框架(唐翎)
Ghost cat 以皮肤为主体的ui框架(唐翎)
 
Js的国(转载)
Js的国(转载)Js的国(转载)
Js的国(转载)
 
Javascript Training
Javascript TrainingJavascript Training
Javascript Training
 
由一个简单的程序谈起――之三(精华)
由一个简单的程序谈起――之三(精华)由一个简单的程序谈起――之三(精华)
由一个简单的程序谈起――之三(精华)
 
JavaScript 快速複習 2017Q1
JavaScript 快速複習 2017Q1JavaScript 快速複習 2017Q1
JavaScript 快速複習 2017Q1
 
從 Singleton 談 constructor
從 Singleton 談 constructor從 Singleton 談 constructor
從 Singleton 談 constructor
 
GTest交流与经验总结
GTest交流与经验总结GTest交流与经验总结
GTest交流与经验总结
 
Dev307
Dev307Dev307
Dev307
 

OOP in C - Virtual Function (Chinese Version)

  • 1. OOP in C Virtual Function elpam.tw@gmail.com elpam@Taiwan, Taipei, 2008
  • 2. LICENSE ● 本投影片授權方式為: – 姓名標示─非商業性─相同方式分享 3.0  台灣版 – http://creativecommons.org/licenses/by­nc­sa/3.0/tw/ ● 所有的範例程式皆為 Public Domain     elpam.tw@gmail.com
  • 3. About This Slides ● All example was build by  – GCC­4.1.3 – GLIB­1.2.10 – GMAKE­3.81     elpam.tw@gmail.com
  • 5. Function Pointer /* 2­1.c */ typedef void (*FP) ( void ); void hello() { printf("hello "); } int main() { void world() { printf("worldn"); }   #> ./2­1 FP fp = hello;  hello world  fp();   #> fp = world; fp(); };     elpam.tw@gmail.com
  • 6. Function Pointer (cont') /* 2­2.c */ ● 也可以當參數使用 typedef void (*FP) ( void ); #define ERROR 1 void error_test( FP callback ) { if( ERROR ){ callback(); } }   #> ./2­2 int main()   error happened  {   #> void error() { printf("error happenedn"); }        error_test( error ); };     elpam.tw@gmail.com
  • 7. Function Pointer & Structure /* 2­3.c */ typedef void (*FP) ( void* ); ● 以 Function Pointer  struct A{         int a;               int b; 的方式實作 Member          FP  method; }; Function void a_real_method( void* p) {         struct A* this = p;         printf("%d,%dn",this­>a,this­>b); } int main() {   #> ./2­3         struct A a;   1,2         a.a = 1;        a.b = 2;   #>         a.method  = a_real_method;         a.method ( &a ); };     elpam.tw@gmail.com
  • 8. Using Previous Slide to Implement Inherit 2­4.c ● 方便閱讀,加上一點 ' 命名規則 ' – 其實是龜毛的 Rule ● PREFIX_init – 該物件的 建構子 (Constructor) ● PREFIX_method – 該物件的 成員函式 (member function)     elpam.tw@gmail.com
  • 9. Member Function's Inherit (1) struct A { void A_real_method_a( void* p) { int a; struct A* this = p; FP  method_a; printf("this is method_a %dn",this­>a);  }; } struct B { void B_real_method_b( void* p) { struct A parent; struct B* this = p; int b; printf("this is method_b %dn",this­>b);  FP  method_b; } }; int main()  { void a_init( struct A* a)  { struct B b; a ­> a = 1; a_init( &b );    a ­> method_a = A_real_method_a;        b_init( &b ); } void b_init( struct B* b)  { struct A* ap = &b; b ­> b = 2; b ­> method_b = B_real_method_b; ap ­> method_a( ap ); } b  .  method_b( &b ); };     elpam.tw@gmail.com
  • 10. Member Function's Inherit (2) /* 2­4.c */ int main() ● Child 如果希望執行 ( 存取 )  { struct B b; Parent 的函式 ( 變數 ) ,需要 a_init( &b );    先 Cast 成 Parent 再執行 ( 存        b_init( &b ); 取) struct A* ap = &b; ap ­> method_a( ap ); b  .  method_b( &b ); };   #> ./2­4   this is method_a 1   this is method_b 2       #> elpam.tw@gmail.com
  • 11. 結論 ● 我們可以實作 class_init() 時將 class 內的 member value and member function 都設定好 – 也就是 ''Constructor''  ● 自已實作 C 不提供的 Member Function!!     elpam.tw@gmail.com
  • 12. Implement Virtual Function 2­5.c ● Child 的 init 可以將 Parent 的 Member Function 做改寫的動作,以達到 Virtual Function 的效果 – 下一頁粉紅色的那一行     elpam.tw@gmail.com
  • 13. Virtual Function (1) void A_real_method_a( void* p)  { struct A* this = p; printf("this is %s %dn"                          ,__FUNCTION__,this­>a);  void A_init( struct A* a) } { void B_real_method_a( void* p)  a ­> a = 1; { a ­> method_a = A_real_method_a; struct B* this = p; } printf("this is %s %dn"                           ,__FUNCTION__,this­>b);  } void B_init( struct B* b) void B_real_method_b( void* p)  { { struct A* a = b; struct B* this = p; b ­> b = 2; printf("this is %s %dn" a ­> method_a = B_real_method_a;                            ,__FUNCTION__,this­>b);  b ­> method_b = B_real_method_b; } }     elpam.tw@gmail.com
  • 14. Virtual Function (2) ● A_init 一定要比 B_init 先執行 – Parent 的 Constructor 需要先執 行 /* 2­5.c */ int main() { struct B b;   #> ./2­5 A_init( &b ); this is A_real_method_a 1 this is B_real_method_a 2 struct A* ap = &b; this is B_real_method_b 2 ap ­> method_a( ap );   #> B_init( &b ); ap ­> method_a( ap ); b  .  method_b( &b ); };     elpam.tw@gmail.com
  • 15. Constructor's Wrapper 2­6.c     elpam.tw@gmail.com
  • 16. Constructor in C (1) ● we use PREFIX_new to replace malloc – 所有的物件都以 PREFIX_NEW 產生,以確保 Constructor 被正確的執行 struct A{ struct A* A_new()    int a; {    int b;    struct A* ret = malloc( sizeof(A) ); };    ret ­> a = 0;    ret ­> b = 1;    return ret; }     elpam.tw@gmail.com
  • 17. Constructor in C (2) ● 以前面的例子 /* 2­6.c */ /* 2­6.c */ int main() struct B* B_new() { {         struct B* pb = B_new();    struct B* pb = malloc( sizeof(B) );    struct A* pa = pb;         ((struct A*)pb) ­> method_a( pb );    A_init( pa );         pb ­> method_b( pb );    B_init( pb );    return pb; }; }     elpam.tw@gmail.com
  • 18. Constructor in C (3) ● 繼承關係越復雜時, PREFIX_new 很難去維護 – 請試想三層繼承時,開發者希望在第一及第二層之間 再加上一層物件 ● 所以我們需要更有效率的方式來撰寫 Constructor – GObject 提供了一個有效率的方式     elpam.tw@gmail.com
  • 19. Conclusion ● 以上的 Tips 提供了一種方式來撰寫 Object­ Oriented 的程式 – 可自行練習 :) ● 相較於 C++ 的繼承,此種方式所撰寫出來的物 件為靜態形別,所有的 Offset 都是 Compiler  Time 已決定好的,所以不會有繼承濫用的問題 – 執行效率 ● 但是如果不正確的使用,依舊會造成程式碼難以   閱讀,也容易產生 BUG  elpam.tw@gmail.com