搜尋此網誌

2011年7月16日 星期六

C++ Reference Variables Usage(C++參考變數的使用)

可以把參考變數(Reference Variable)想像成一個變數的別名或替代名稱.而且此變數和原來的變數存在於共同的記憶體位置,並且擁有相同的值.

#include <iostream>
using namespace std;

int main() {
int a=1;
int & a1=a;//a1 is a reference variable
cout << a1 <<endl;
return 0;
}



之前有提過c++和Java的基本型別變數(int ,double等)都是call by value的
call by reference or value若是想要call by reference,在c++可以用reference帶替pointer(指標)當作傳入函式的參數.如下例:

#include <iostream>
using namespace std;
void sum4(int &);

int main() {
int a=1;
sum4(a);
cout << a <<endl;
return 0;
}

void sum4(int & a) {
a=2;
}



在這個例子中,雖然並沒有建立一個reference變數,但當基本變數a傳入此function sum4()的時候,會自動被當成reference變數來對待,也就是call by reference,因此在函式內改變a的值之後,
原本變數a的值也會一起被改變.

  • Reference變數也可以當作函式的回傳值.


  • #include <iostream>
    using namespace std;
    int & sum5(int &);

    int main() {
    int a=1;
    sum5(a)=3;
    cout << a << endl;
    return 0;
    }

    int & sum5(int &a){
    return a;
    }



    因為sum5回傳的是(reference),也就是記憶體位置,因此改變a的值為3,也會同時改變原本的變數值.若在sum5的前方加上關鍵字const,那麼我們便不能直接使用sum5所return回來的reference來改變變數值,如下例子:

    #include <iostream>
    using namespace std;
    const int & sum5(int &);

    int main() {
    int a=1;
    sum5(a)=3;
    cout << a << endl;
    return 0;
    }

    const int & sum5(int &a){
    return a;
    }

    "那些年,我們一起追的女孩,觀後感"

    C++ 變數的生存範圍和種類

    C++的變數範圍(Scope)有三種

    • 區域變數(Local Variables):在函式內宣告的變數,當跳離或函式結束執行的時候,此變數的記憶體空間會自動被回收

    • 靜態變數(Static Variables):在程式主體和函式之間的變數.程式結束執行的時候記憶體會自動被作業系統回收

    • 動態變數(Dynamic Variables):實際執行時期用到的變數.要用delete手動把存在記憶體的變數值刪掉,或是程式結束執行的時候會被作業系統自動回收.



    #include <iostream>
    using namespace std;

    void sum3(int);
    int main() {
    int a=1;//Static Variable
    sum3(a);
    int * ptr=new int;//Dynamic Variable
    *ptr=2;
    cout << "before delete: "<<endl;
    cout << *ptr<<endl;
    delete ptr;
    cout << "after delete:" <<endl;
    cout << *ptr<<endl;
    return 0;
    }

    void sum3(int a) {
    int b=a;//Local Variable
    cout << b<<"\n";
    }

    C++ Namespace(命名空間)用法

    c++的namespace和Java的package有異曲同工之妙,也就是說宣告在不同namespace的function.即便擁有同樣的名字也不會衝突到,可獨立使用.
    以下是範例程式:
    #include <iostream>
    using namespace std;

    namespace MyException {
    class Exception {
    public:
    void mesg() {
    cout << "Exception Occurred !!"<<endl;
    }
    };
    }


    void sum2(int, int) throw (MyException::Exception);
    int main() {
    int a=1;
    int b=1;
    try {
    sum2(a, b);
    } catch (MyException::Exception & ex) {// start of exception handler
    ex.mesg();
    }
    return 0;
    }

    void sum2(int a, int b) throw (MyException::Exception) {
    if (a==b) {
    throw MyException::Exception();
    }
    cout << a+b<<"\n";
    }




    解說:
    先命名一個namespace為MyException的block,然後在block內定義一個Exception類別,接下來使用"命名空間::類別名稱"來使用此類別


    也可以使用兩個namespace的方式來更進一步減少name collision,不過在使用的時候要記得存取每一層namespace的名字,compile才有辦法正確找到要使用的類別.


    namespace MyException {
    namespace SecondLevel {
    class Exception {
    public:
    void mesg() {
    cout << "Exception Occurred !!"<<endl;
    }
    };
    }
    }