2018年6月16日 星期六

函式指標

函數指標:
宣告函式指標,並讓它與某個函式指向相同的空間

標準式:
傳回值型態 (*指標名稱)(傳遞參數); ->程式會給你指向函數的地址,並依其做操作

如果函式帶有參數,則函式指標本身的宣告也必須指定相同的參數型態與個數,下面這個程式用來顯示重載函式會分別佔據不同的記憶體空間: 

#include  
using namespace std; 

int foo(int, int); 
char foo(int, char); 

int main() { 
    int (*ptr1)(int, int) = 0; 
    char (*ptr2)(int, char) = 0; 

    ptr1 = foo; // get address of foo(int, int) 
    ptr2 = foo; // get address of foo(int, char) 

    ptr1(1, 2); 
    ptr2(3, 'c'); 

    cout << "address of foo(int, int): " 
         << (int)ptr1 << endl; 
    cout << "address of foo(int, char): " 
         << (int)ptr2 << endl; 

    return 0; 
} 

int foo(int n1, int n2) { 
    cout << "foo(int, int): " 
         << n1 << "\t" << n2 
         << endl;

    return 0; 
} 

char foo(int n, char c) { 
    cout << "foo(int, char): " 
         << n << "\t" << c 
         << endl;

    return c; 
}
執行結果:
foo(int, int): 1        2
foo(int, char): 3       c
address of foo(int, int): 4199548
address of foo(int, char): 4199648

  • 應用
  • 可以在一個函數裡面放入一個另外名字的函數指標,使用者為其放入需要的特定函式
  • #include "sort.h";
    void swap(int &a, int &b) {
        int t = a; 
        a = b; 
        b = t;
    }
    bool larger(int a, int b) {
        return a > b;
    }
    bool smaller(int a, int b) {
        return a < b;
    }//要放入的人
    void sort(int* arr, int length, bool (*compare)(int, int)) { 
        int flag = 1; 
        for(int i = 0; i < length-1 && flag == 1; i++) { 
            flag = 0; 
            for(int j = 0; j < length-i-1; j++) { 
                if(compare(arr[j+1], arr[j])) { 
                    swap(arr[j+1], arr[j]); 
                    flag = 1; 
                } 
            } 
        } 
    }
  • 縮寫亦可
  • typedef bool (*CMP)(int, int);
    void swap(int&, int&);
    bool larger(int a, int b);
    bool smaller(int a, int b);
    void sort(int*, int, CMP);
  • 要注意的是:紅色標註地方,不適用於靜態函數呼叫,由於靜態函數為類別而非物件,所以必須使用呼叫而非".","->"
  • typedef void (SafeArray::*MFPTR1)(int, int);     typedef int (SafeArray::*MFPTR2)(int); MFPTR1 mfPtr1 = 0; MFPTR2 mfPtr2 = 0;
    為了取得一個成員函式的位址值,您可以使用&取址運算子並指明是哪個類別的哪個成員函式,例如:
    mfPtr1 = &SafeArray::set; mfPtr2 = &SafeArray::get;
    成員函式在記憶體中只會存在一份,在調用成員函式時,具體要配合實際的物件位址,物件位址會是 this 指標 指向的位址,所以透過物件調用成員函式的方式如下:
    SafeArray safeArray(10); // 以下與safeArray.set(2, 10) 相同 (safeArray.*mfPtr1)(2, 10); // 以下的成員函式呼叫部份與safeArray.get(2)相同
    cout << (safeArray.*mfPtr2)(2) << endl;
    "." 運算子之後使用*對指標取值,括號是給定引數。如果是物件指標的話,則可以如下:
    SafeArray *safePtr = &safeArray;// 以下相當於safePtr->set(2, 100) (safePtr->*mfPtr1)(2, 100);

沒有留言:

張貼留言

Ethereum- Learn Solidity step by step

Common Function Types: public: Anyone can call this function,but it isn't really used for any type of security per se. priv...