第二章 C++概述

/*
 1.const修飾符用法
 2.內聯函數
 3.帶默認參數的函數
 4.函數的重載
 5.作用域運算符::
 6.共用體
 7.運算符new和delete
 8.引用
 9.應用舉例
 */
#include <iostream>
#include <cmath>
using namespace std;
void testFun1();
void testFun2();
void testFun3();
void testFun4();
void testFun5();
void testFun6();
void testFun7();
void testFun8();
void testFun9();
int main(int argc, const char * argv[]) {
//    testFun1();
//    testFun2();
//    testFun3();
//    testFun4();
//    testFun5();
//    testFun6();
//    testFun7();
//    testFun8();
    testFun9();
    return 0;
}
//1.const修飾符
void testFun1(){
//    1、定義常量
//    (1)const修飾變量,以下兩種定義形式在本質上是一樣的。它的含義是:const修飾的類型爲TYPE的變量value是不可變的。

    int const Value1 = 10;
    const int Value2 = 18;
//    Value1 = 20; ❌
//    Value2 = 30; ❌
    cout<<Value1<<endl<<Value2<<endl;

//    (2)將const改爲外部連接,作用於擴大至全局,編譯時會分配內存,並且可以不進行初始化,僅僅作爲聲明,編譯器認爲在程序其他地方進行了定義.
//    extend const int ValueName = value;

    //2、與指針結合
    int a = 30;
    int b = 60;
    //1)指向常量的指針 指針的內容不能改變,但是指針的指向是可以改變的
    const int *p1 = &a;
    cout<<"address:"<<p1<<"   value:"<<*p1<<endl;
    p1 = &b;
//    *p1 = b;❌
    cout<<"address:"<<p1<<"   value:"<<*p1<<endl;

    const char *name = "fanhua";
    name = "chendian";
    cout<<name<<endl;
//    name[0] = 'c';❌
    //2)常指針 指針所指的內容可以改變,但是指針本身的指向不能改變
    int *const p = &a;
    cout<<"address:"<<p<<"   value:"<<*p<<endl;
    *p = b;
//    p = &b;  ❌
    cout<<"address:"<<p<<"   value:"<<*p<<endl;
    char *const nickname = "fanhua";
//    nickname = "chendian";❌
//    nickname[0] = 'c';
    cout<<nickname<<endl;
    //3)指向常量的常指針  內容和指向都不能改變
    const int* const p3 = &a;
//    p3 = &b;❌
//    *p3 = b;❌
    cout<<"address:"<<p3<<"   value:"<<*p3<<endl;

    const char* const aliasname = "chen";
//    aliasname[3] = 'd';❌
//    aliasname = "zhang";❌
    cout<<aliasname<<endl;
    /*
     const修飾指針變量時:

       (1)只有一個const,如果const位於*左側,表示指針所指數據是常量,不能通過解引用修改該數據;指針本身是變量,可以指向其他的內存單元。

       (2)只有一個const,如果const位於*右側,表示指針本身是常量,不能指向其他內存地址;指針所指的數據可以通過解引用修改。

       (3)兩個const,*左右各一個,表示指針和指針所指數據都不能修改。
     */
    //3、與函數結合使用const
//    void testModifyConst(const int x);在函數內部參數值不會改變;
}
/*
 2.內聯函數(內置函數)
   聲明 函數說明前冠以關鍵字 inline
    每當程序中出現對該函數的調用時,C++編譯器是函數體中的代碼塊插入到調用函數的語句處(相當於把代碼複製一份到調用位置,而不發生真正的函數調用)。
    作用:消除函數調用時候的系統開銷,以提高程序的執行效率。在程序執行過程中調用函數時,系統將程序當前的一些狀態信息存到棧中(例如現場和返回地址等),同時轉到函數的代碼處去執行函數體語句,這些參數的保存與傳遞的過程中須要時間和空間的開銷,使得程序執行效率低。內聯函數是一種犧牲空間換區時間的處理方法。
 */
inline int box(int a, int b, int c){
    return a * b * c;
}
void testFun2(){
    int e = box(1, 2, 3);
    cout<<e<<endl;
}
/*
 3.帶默認參數的函數
 */
int sum(int a = 1, int b = 2, int c = 3){
    return a + b + c;
}
void testFun3(){
    int e = 0;
    e = sum();
    cout<<e<<endl;
    e = sum(100);
    cout<<e<<endl;
    e = sum(100,300);
    cout<<e<<endl;
    e = sum(100,200,300);
    cout<<e<<endl;
//    e = sum(,200);❌
}

/**
 4.函數的重載(注意:只有返回值不同構不成函數重載)
 */
int mul(int a, int b){
    return a + b;
}
int mul(int a, int b, int c){
    return a + b + c;
}
//float mul(float a, float b){
//    return a + b;
//}

double mul(double a, double b){
    return a + b;
}
float mul(float a, float b , float c, float d){
    return a + b + c + d;
}
void testFun4(){
    int e = 0;
    float f = 0.0;
    e = mul(2, 3);
    cout<<e<<endl;
    e = mul(2, 4, 5);
    cout<<e<<endl;
    double d = mul(2.4, 3.4);
    cout<<d<<endl;
    f = mul(2.4, 4.4, 5.5, 5.6);
    cout<<f<<endl;
}
/*
 5.作用域運算符::
 */
int avar = 1314;
void testFun5(){
    int avar = 0;
    avar = 520;
    cout<<"lobal: "<<avar<<endl;
    cout<<"global: "<<::avar<<endl;
    ::avar = 520;
    cout<<"global: "<<::avar<<endl;
}
/*
 6.共用體
 */
void testFun6(){
    union data{
        long int i;
        double d;
        char c;
    };
    //無名共用體
    union {
        int i;
        double d;
        float f;
    }x;
    cout<<sizeof(data)<<endl;
    cout<<&x.i<<endl;
    cout<<&x.d<<endl;
    cout<<&x.f<<endl<<endl;

    union data d;
    d.c = 'a';
    cout<<d.i<<endl;
    cout<<d.d<<endl;
    cout<<d.c<<endl<<endl;

//    x.i = 65;
//    cout<<x.i<<endl;
//    cout<<x.d<<endl;
//    cout<<x.f<<endl<<endl;
    x.d = 65.0;
    cout<<x.i<<endl;
    cout<<x.d<<endl;
    cout<<x.f<<endl;
}
/*
 7.運算符new 與 delete 動態分配內存空間
 */
void testFun7(){
    int *p;
    p = new int(10);
    if (!p) {
        cout<<"allocaction failure!\n";
        return;
    }
    cout<<*p<<endl;
    cout<<p<<endl<<endl;
    delete p;
    p = new int;
    *p = 520;
    cout<<*p<<endl;
    cout<<p<<endl<<endl;
    delete p;
    int *array = new int[3];
    array[0] = 1;
    array[1] = 2;
    array[2] = 3;
    for (int i = 0 ; i < 3; i++) {
        cout<<array[i]<<endl;
    }
    delete [] array;
}
/*
 8.引用
 建立引用的作用是爲變量另起一個名字,變量的引用通
 常被認爲是變量的別名。當生命了一個引用時,必須同
 時用另一個變量名來將它初始化,即聲明它代表哪一個變
 量,是哪一個變量的別名。這樣,對一個引用的所有操作,
 實際上都是對其所代表的變量的操作,就如同對一個人來說,
 即使有三四個名字,實際上就是同一個人,用這三四個名字
 所做的事情,其實就是那一個人所做的事情。

 類型 &引用名 = 已定義的變量名;
 */
void sample(){
    int i;
    int &j = i;
    i = 30;
    cout<<"i="<<i<<" j="<<j<<endl;
    j = 50;
    cout<<"i="<<i<<" j="<<j<<endl;

    cout<<"變量 i 的地址: "<<&i<<endl;
    cout<<"引用 j 的地址: "<<&j<<endl;
}
//引用作爲函數參數
void swap(int &m , int &n){
    int temp = m;
    m = n;
    n = temp;
}
//引用作爲函數返回值
int &max(int &num1, int &num2){
    return (num1>num2)?num1:num2;
}
int &min(int &num1, int &num2){
    return num1<num2?num1:num2;
}
void testFun8(){
    sample();
    int num1 , num2;
    cout<<"請輸入第一個數:";
    cin>>num1;
    cout<<"請輸入第二個數:";
    cin>>num2;
    cout<<"\n找出最大數,然後把最大數賦爲0後,兩個分別爲:"<<endl;
    max(num1, num2) = 0;
    cout<<num1<<"和"<<num2<<endl;
    cout<<"現在請再輸入兩個數:"<<endl;
    cout<<"請輸入第一個數:";
    cin>>num1;
    cout<<"請輸入第二個數:";
    cin>>num2;
    cout<<"\n找出最小數,然後把最小數賦爲0後,兩個分別爲:"<<endl;
    min(num1, num2) = 0;
    cout<<num1<<"和"<<num2<<endl;
}

/*
 9.應用舉例
 */
//1)引用的理解
int &f(int &i){
    i += 10;
    return i;
}
void testSample1(){
    int k = 0;
    int &m = f(k);
    cout<<k<<endl;
    m = 50;
    cout<<k<<endl;
}

//2)用動態分配空間的方法計算Fibonacci數列的前20項
//  並存儲到動態分配的空間中
/*
 斐波那契(Fibonacci)數列指的是這樣一個數列 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233,377,610,987,1597,2584,4181,6765,10946,17711,28657,46368........
 自然中的斐波那契數列
 自然中的斐波那契數列
 這個數列從第3項開始,每一項都等於前兩項之和。
 */
void testSample2Fibonacci(){
    int *p = new int[20];
    *p = 1;
    *(p + 1) = 1;
    cout<<*p<<"\t"<<*(p + 1)<<"\t";
    p = p + 2;
    for (int i = 3; i <= 20; i++) {
        *p = *(p - 1) + *(p - 2);
        cout<<*p<<"\t";
        if (i % 5 == 0) {
            cout<<endl;
        }
        p++;
    }
}
//3)百錢問題:將一元人民幣兌換成1、2、5分硬幣,有多少種換髮?
void testSample3(){
    int n_five;
    int n_two;
    int n_one;
    int sum = 0;
    for (n_five = 0; n_five <= 20; n_five++) {
        for (n_two = 0; n_two <= 50; n_two++) {
            n_one = 100 - n_five * 5 - n_two * 2;
            if (n_one >= 0) {
                cout<<"一分:"<<n_one<<"\t二分:"<<n_two<<"\t五分:"<<n_five<<endl;
                sum++;
            }
        }
    }
    cout<<"sum = "<<sum<<endl;
}
//4)用二分法求解 f(x)=0 的根? 不理解
inline int fun(float x){
    return 2 * x * x * x - 4 * x * x + 3 * x - 6;
}
void testSample4(){
    float left, right, middle, ym, yl, yr;
    cout<<"please two number :"<<endl;
    cin>>left>>right;
    yl = fun(left);
    yr = fun(right);

    do {
        middle = (right + left)/2;
        ym = fun(middle);
        if (ym * yr > 0) {
            right = middle;
            yr = ym;
        }else{
            left = middle;
            yl = ym;
        }
    } while (fabs(ym) >= 1e-6);
    cout<<"\nRoot is : "<<middle<<endl;
}
void testFun9(){
    testSample1();
    cout<<"***********************"<<endl;
    testSample2Fibonacci();
    cout<<"***********************"<<endl;
    testSample3();
    cout<<"***********************"<<endl;
    testSample4();

}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章