【C++学習】文法速成3

9048 ワード

文書ディレクトリ
  • 解析関数
  • 構造関数と構造関数の応用
  • 静的メンバー変数および静的メンバー関数
  • メンバーオブジェクトおよびクローズドクラス
  • 友元
  • thisポインタ
  • 定数オブジェクト、定数メンバー関数、および定数参照
  • こうぞうかんすう
    コンストラクション関数は主にオブジェクトを初期化するために使用され、コンストラクション関数は主に後始末オブジェクトの消滅に使用されます.
    特徴:
  • 名前はクラス名と同じ(コンストラクタを区別するために前に加算~)
  • パラメータと戻り値がない
  • クラスは最大1つの構造関数
  • しかありません.
    オブジェクトが消滅すると、構造関数が自動的に呼び出され、割り当てられた空間を解放するなど、オブジェクトが消滅する前に後始末をします.
    クラスを定義するときに構造関数を書かないと、コンパイラはデフォルトの構造関数を自動的に生成します(何もしません).
    class String
    {
    	private:
    		char * p;
    	public:
    		String()
    		{
    			p=new char[10];
    		}
    		~ String();		//      
    };
    String::~ String()
    {
    	delete [] p;	//      
    }
    

    オブジェクト配列のライフサイクルが終了すると、オブジェクト配列の各要素の構造関数が呼び出されます.
    delete演算を使用すると、構造関数が呼び出されます.
    Ctest * pTest;
    pTest = new Ctest;		//      
    delete pTest;		//      
    pTest = new Ctest[3];	//      3 
    delete [] pTest;		//      3 
    

    構造関数と構造関数の応用
    class Demo
    {
    	int id;
    	public:
    		Demo(int i)
    		{
    			id=i;
    			cout<

    静的メンバー変数と静的メンバー関数
  • メンバー変数とメンバー関数の前にstaticを加えると静的メンバー変数と静的メンバー関数になります.
  • class CRectangle
    {
    	private:
    		int w,h;
    		static int nTotalArea;		//      
    		static int nTotalNumber;
    	public:
    		CRectangle(int w_,int h_);
    		~CRectangle();
    		static void PrintToal();	//      
    };
    
  • 静的メンバー変数は、すべてのオブジェクトで共有されます.(sizeof関数は静的メンバー変数を計算しません)
  • 静的メンバー関数は、オブジェクトには特に作用しません.
  • 静的メンバーは、オブジェクトを介してアクセスする必要はありません.

  • 静的メンバーへのアクセス方法:
    CRectangle::PrintTotal();		//        
    
    CRectangle r;		//              
    r.PrintTotal();		
    
    CRectangle * p=&r;	//      
    p->PrintTotal();
    
    CRectangle & ref = r;		//      
    int n = ref.nTotalNubmber;
    

    静的メンバー変数は本質的にグローバル変数であり、オブジェクトがなくても静的メンバー変数が存在します.
    静的メンバー関数は本質的にグローバル関数です.
    class CRectangle
    {
    	private:
    		int w,h;
    		static int nTotalArea;		//      
    		static int nTotalNumber;
    	public:
    		CRectangle(int w_,int h_);
    		~CRectangle();
    		static void PrintToal();	//      
    };
    CRectangle::CRectangle(int w_,int h_)		//    
    {
    	w=w_;
    	h=h_;
    	nTotalNumber ++;
    	nToalArea += w*h;
    }
    CRectangle::~CRectangle()		//    
    {
    	nTotalNumber --;
    	nTotalArea -= w*h;
    }
    void CRectangle::PrintTotal()
    {
    	cout<
  • 静的メンバー関数では、非静的メンバー変数にアクセスできず、非静的メンバー関数を呼び出すことはできません.(非静的メンバー変数がどのクラスに属するか不明)
  • 上のコードにはレプリケーションコンストラクタが書かれていません.ケンはCRectangleクラスオブジェクトを返すときに、システムがデフォルトのレプリケーションコンストラクタを呼び出し、nTotalNumberとnTotalAreaが追加されないようにします.

  • メンバー・オブジェクトと閉じたクラス
  • メンバーオブジェクト:クラスのメンバー変数が別のクラスのオブジェクト
  • です.
  • メンバーオブジェクトを含むクラスを閉鎖クラス
  • と呼ぶ.
    class CTyre
    {
    	private:
    		int radius;
    		int width;
    	public:
    		CTyre(iny r,int w):radius(r),width(w){}		//     (      )
    };
    class CEngine
    {
    };
    class CCar
    {
    	private:
    		int price;
    		CTyre tyre;
    		CEngine engine;
    	public:
    		CCar(int p,int tr,int tw);
    };
    CCar::CCar(int p,int tr,int tw):price(p),tyre(tr,w)		//     
    {
    
    };
    int main()
    {
    	CCar car(20000,17,225);		//  20000,19  ,225  
    	return 0;
    }
    

    上記のCCarクラスでコンストラクション関数が定義されていない場合、コンパイラはCCarのtyreがどのように初期化されているか分からないため、コンパイルエラーが発生します(engineメンバーオブジェクトはデフォルトのコンストラクション関数を使用しているため、問題ありません).
  • 初期化リスト:クラス名::コンストラクション関数(パラメータテーブル):メンバー変数1(パラメータテーブル)、メンバー変数2(パラメータテーブル)......
  • 閉じたクラスオブジェクトを生成する場合:まず、すべてのオブジェクトのコンストラクション関数(閉じたクラスで説明されている順序と一致し、初期化リストの出現順序とは無関係)を実行し、閉じたクラスのコンストラクション関数を実行します.
    クラスオブジェクトが消滅した場合:まずクラスを閉じた構造関数を実行し、次にメンバーオブジェクトの構造関数を実行します.
    すなわち,構造関数は構造関数の呼び出し順序とは逆に,先に構築された後に消滅する.
    友元
    友元は次のように分けられます.
  • 友元関数
  • 友元類
  • クラスのメタ関数は、クラスのプライベートメンバーにアクセスできます.
    class CCar;		//    ,    CDriver   
    class CDriver
    {
        public:
        	void Modify(CCar * pCar);	//    
    };
    class CCar
    {
        private:
        	int price;
        friend int MostExpensiveCar(CCar cars[],int total);		//      
        friend void CDriver::ModifyCar(CCar * pCar); //      , ModifyCar()     
    };
    void CDriver::ModifyCar(CCar * pCar)
    {
        pCar->price += 1000;	//         
    }
    int MostExpensiveCar(CCar cars[],int total)
    {
        int tmpMax = -1;
        for (int i=0;itmpMax)
                tmpMax=cars[i].price;
        return tempMax;
    }
    int main()
    {
        return 0;
    }
    

    友元関数に加えて、クラスを別のクラスの友元として定義することもできます.
    AがBの友元クラスである場合、Aのメンバー関数はBのプライベートメンバーにアクセスすることができる.
    class CCar
    {
    	private:
    		price;
    	friend class CDriver;
    };
    class CDriver
    {
    	public:
    		CCar myCar;
    		void ModifyCar()
    		{
    			myCar.price += 1000;
    		}
    };
    int main()
    {
    	return 0;
    }
    

    thisポインタ
    C++プログラムの初期コンパイルでは、C++プログラムをCプログラムに翻訳する必要があります.メンバー関数はグローバル関数になります.グローバル関数はメンバー関数よりもthisポインタが1つ多くなります.
    翻訳プロセスの例:
    //C++  
    class CCar
    {
        public:
        	int price;
            void SetPrice(int p);
    };
    void CCar::SetPrice(int p)
    {
        price=p;
    }
    int main()
    {
        CCar car;
        car.SetPrice(20000);
        return 0;
    }
    
    //C  
    struct CCar
    {
        int price;
    };
    void SetPrice(struct CCar * this,int p)	//         this  
    {
        this->price=p;
    }
    int main()
    {
        struct CCar car;
        SetPrice(&car,20000);
        return 0;
    }
    

    次のプログラムはthisポインタで理解する必要があります
    class A
    {
    	int i;
        public: void Hello(){cout<Hello();		//     Hello   C   ,      p,        
    }
    

    静的メンバー関数ではthisポインタは使用できません!
    静的メンバー関数はオブジェクトに作用しないためです.
    したがって,静的メンバ関数の真のパラメータ個数はプログラムに書かれたパラメータ個数である.
    定数オブジェクト、定数メンバー関数、および一般参照
  • 定数オブジェクト
  • オブジェクトの値を変更したくない場合は、オブジェクトを定義するときにconstキーを前に付けることができます.
    class Demo
    {
    	private:
    		int value;
    	public:
    		void SetValue(){}
    };
    const Demo Obj;	//    
    
  • 定数メンバー関数
  • クラスのメンバー関数の説明の後にconstキーを付けることができます.このメンバー関数は定数メンバー関数と呼ばれます.
    定数メンバー関数の実行中に、その役割を変更するオブジェクトは変更されません.したがって、定数メンバー関数では、メンバー変数の値(静的メンバー変数を除く)を変更することはできません.また、同じクラスの非常量メンバー関数(静的メンバー関数を除く)を呼び出すこともできません.
    class Sample
    {
        public:
        	int value;
        	void GetValue() const;
        	void func(){};
        	Sample(){}
    };
    void Sample::GetValue() const
    {
        value=0;	//wrong,          
        func();		//wrong,           
    }
    int main()
    {
        const Smaple o;
        o.value=100;	//wrong,         
        o.func();		//wrong,                
        o.GetValue();	//OK,          
        return 0;
    }
    

    2つのメンバー関数、名前とパラメータは同じですが、1つはconstで、1つはそうではありません.では、この2つのメンバー関数は再ロードされます.
    class  CTest
    {
        private:
        	int n;
        public:
        	CTest(){n=1;}
        	int GetValue() const {return n;}
        	int GetValue() {return 2*n;}
    };
    int main
    {
    	const CTest objTest1;
    	CTest objTest2;
    	cout<
  • 常引用
  • 参照の前にconstキーワードを付けて、常参照と呼ぶことができます.参照される変数は、通常の参照では変更できません.関数パラメータとしてよく使用されます.
    一般オブジェクトは関数パラメータとして使用され、このパラメータを生成するにはレプリケーション構造関数を呼び出す必要があり、効率が比較的高い.ポインタをパラメータとして使うと、コードが面白くないので、参照をパラメータとして使うことができます.次のようになります.
    class Sample
    {
    	……
    };
    void PrintObj(Sample & o)
    {
    	……
    }
    

    しかし、オブジェクト参照は関数パラメータとして一定のリスクがあり、関数内でパラメータoを変更すると、実パラメータも変化し、この場合、オブジェクトの常参照をパラメータとして使用することができます.
    class Sample
    {
    	……
    };
    void PrintObj(const Sample & o)
    {
    	……
    }
    

    objTest2; cout< return 0; }
    
    *    
    
             const   ,     。              。       。
    
               ,               ,     。         ,      ,           。 :
    
    ~~~c++
    class Sample
    {
    	……
    };
    void PrintObj(Sample & o)
    {
    	……
    }
    

    しかし、オブジェクト参照は関数パラメータとして一定のリスクがあり、関数内でパラメータoを変更すると、実パラメータも変化し、この場合、オブジェクトの常参照をパラメータとして使用することができます.
    class Sample
    {
    	……
    };
    void PrintObj(const Sample & o)
    {
    	……
    }