青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

隨筆 - 60, 文章 - 0, 評論 - 197, 引用 - 0
數據加載中……

C++ 學習筆記

一   編程設計
     1.將程序劃分為多個子系統,包括子系統間的接口和依賴關系、子系統間的數據流、在各子系統間的來回輸入輸出、以及總的線程模型。

     2.各個子系統的具體細節,包括進一步細分的類、類層次體系、數據結構、算法、特定的線程模型和錯誤處理。

二   設計流程
     1.需求:功能需求和性能需求。
     2.設計步驟
       (1)把程序劃分為通用功能子系統,并明確子系統的接口和交互。
       (2)把這些子系統列在一個表中,并表示出子系統的高層行為或功能、子系統向其它子系統提供的接口,及此子系統使用了其他子系統的哪些接口。
       (3)選擇線程模型:確定使用多少個線程,明確線程的交互并為共享數據指定加鎖機制。
       (4)為每個子系統指定層次體系
       (5)為每個子系統指定類、數據結構、算法和模式
       (6)為每個子系統指定錯誤處理(系統錯誤 + 用戶錯誤),指定是否使用異常

三   C++ 的設計原則
     1.抽象:將接口與實現相分離
     2.重用:代碼重用和思想重用

四   對象關系
     1.has-a 關系(聚集)
     2.is-a  關系(繼承)
     3.組織對象層次體系:
      (1)將類按有意義的功能加以組織。
      (2)將共同的功能放到超類中,從而支持代碼重用。
      (3)避免子類過多的覆蓋父類的功能。

五   重用設計
     1.建立可重用的代碼結構
      (1)避免將無關或邏輯上分離的概念混在一起
      (2)把程序劃分為子系統
      (3)使用類層次體系來分離邏輯概念
      (4)使用聚集來分離邏輯概念
      (5)對通用數據結構和算法使用模板
      (6)提供適當的檢查和防護

六   設計易于使用的接口
     1.開發直觀的接口
     2.不要遺漏必要的功能
     3.提供簡潔的接口
      (1)消除重復的接口
      (2)只提供所需的功能
      (3)適當的限制庫的使用
     4.提供文檔和注釋
      (1)公共的文檔應指定行為,而不是底層實現

七   設計通用的接口
     1.提供多種方法來完成同一功能
     2.提供定制能力

八   協調一般性和通用性
     1.提供多個接口
     2.優化常用功能

九   代碼注釋
     (1)前綴注釋
        * 文件/類名
        * 最后一次修改時間
        * 原作者
        * 文件所實現特性的編號 (特性 ID)
        * 版權信息
        * 文件/類的簡要描述
        * 未完成的特性
        * 已知的 bug

     (2)注釋示例
        /*
         * Watermelon.cpp
         *
         * $Id: Watermelon.cpp,v 1.6 2004/03/10 12:52:33 klep Exp $
         *
         * Implements the basic functionality of a watermelon. All
         * unit are expressed in terms of seeds per cubic centimeter
         * Watermelon theory is based on the white paper "Alogorthms
         * for Watermelon Processing."
         *
         * The following code is (c)copyright 2004. FruitSoft, Inc.
         * All right reserved
         */

十   編寫代碼
     1.類定義在 C++ 中是一條語句,因此必須以分號結束。
     2.:: 指作用域解析操作符。
     3.在棧和堆上使用對象的區別
       (1)在棧上創建對象
          SpreadsheetCell myCell, anotherCell;

       (2)在堆上使用對象
          SpreadsheetCell *myCellp = new SpreadsheetCell();

       (3)如果用 new 來分配一個對象,用完該對象時要用 delete 來釋放

     4.C++ 程序員通常把構造函數稱為 "ctor"

     5.使用構造函數
       (1)在棧上使用構造函數
          SpreadsheetCell myCell(5);

       (2)在堆上使用構造函數
          SpreadsheetCell *myCell = new SpreadsheetCell(5);
          delete myCell;

       (3)不要嘗試從類的一個構造函數調用另一個構造函數

     6.使用默認構造函數
       (1)在棧上使用構造函數
          SpreadsheetCell myCell;  //right
          SpreadsheetCell myCell();//wrong

       (2)在棧上創建對象時,要去掉默認構造函數的小括號
       (3)在堆上使用默認構造函數
          SpreadsheetCell *myCellp = new SpreadsheetCell();

       (4)什么時候需要使用構造函數
          SpreadsheetCell cells[3];//fails comilation without default ctor
         SpreadsheetCell *myCellp = new SpreadsheetCell[10];//alse fails

       (5)使用初始化列表
          1)初始化列表允許在創建數據成員的同時完成數據成員的初始化
          2)使用初始化列表的情況

      數據成員                                         解釋
      ------------------------------------------------------------------
      const 數據成員                              必須在創建時提供值
      引用數據成員                               引用無法獨立存在
      沒默認構造函數的對象成員       對象成員無法初始化
      沒有默認構造函數的超類           見后面 
      ------------------------------------------------------------------

     7.對象的撤銷
       (1)析構函數僅用于釋放內存或釋放其他資源是一個不錯的想法

     8.淺復制與深復制
       (1)淺復制:只是從源對象直接將數據成員復制或賦值到目標對象
       (2)深復制:非淺復制
       (3)只要在類中動態分配了內存,就應該編寫自己的復制構造函數來提供內存的深復制
       (4)在對一個對象進行賦值前,必須先釋放此對象的所有動態分配的內存
       (5)只要類會動態分配內存,就需要編寫析構函數、復制構造函數、賦值操作符
       (6)禁止對象賦值,可將復制構造函數與賦值操作符聲明為私有成員
       (7)不必為私有復制構造函數和賦值操作符提供實現,編譯器不要求

十一 精通類和對象
     1.不能在靜態方法中訪問非靜態數據成員
     2.保證一個對象不會修改數據成員,可用 const 來標記

     3.保證一個方法不會修改數據成員,可用 const 來標記
       (1)在類定義中的聲明 double getValue() const;
       (2)在源文件中的實現
          double Spreadsheet::getValue() const
         {
            return this.mValue;
         }

     4.非 const 對象可以調用 const 和非 const 方法,const 對象只能調用const 方法

     5.應將所有不會修改對象的方法都聲明為 const,并在程序中使用 const對象引用

     6.將變量置為 mutable,這樣編譯器允許在 const 方法中修改這個變量
     7.C++ 不允許僅基于方法的返回類型而重載一個方法名
     8.默認參數:從最右參數開始的連續參數表
     9.只能在方法聲明中指定默認參數,在定義中并不指定
     10一個構造函數的所有參數都有默認值,此函數會作為默認構造函數
     11能利用默認參數做到的事情,利用方法重載也可以做,用你最熟悉的

     12內聯:將方法體或函數體直接插入到代碼調用處(相當于 #define 宏的安
       全版本),內聯示例如下:

       (1)在類的源文件(SpreadsheetCell.cpp)
       inline double SpreadsheetCell::getValue() const
       {
           mNumAccess++;
           return mValue;
       }

       (2)或在類的聲明文件中直接實現此方法而不用 inline 關鍵字
       //SpreadsheetCell.h
       double getValue() const (mNumAccesses++; return mValue;}

     13友元可以訪問指定類中的 protected 和 private 數據成員和方法
       (1)聲明友元類
          class SpreadsheetCell
          {
             public:
                 friend class Spreadsheet;
                //code omitted here
          };

       (2)聲明友元方法
          class SpreadsheetCell
         {
             public:
                 friend bool checkSpreadsheetCell();
                 //code omitted here
         };


十二 C++ 中的繼承機制
     1.超類指針(引用)在引用子類時,了類仍然會保留它們覆蓋的方法。而在
       強制類型轉換成超類對象時,子類會失去它們的獨有特性。覆蓋方法和子
       類數據的丟失稱為切割。

     2.作為一條經驗,要把所有的方法都用 virtual 聲明 (包括析構函數,但
       是不包括構造函數) 來避免因遺漏關鍵字 virtual 而產生的相關問題。

     3.virtual 用法示例:
       class Sub : public Super
       {
           public:
           Sub();
           virtual void someMethod();
           virtual void someOtherMethod();
       }

     4.要把所有的析構函數都用 virtual 聲明

     5.強制類型轉換
       (1)靜態轉換 static_cast<type>
          示例:
          Sub* mySub = static_cast<Sub*>(inSuper);

       (2)動態轉換 dynamic_cast<type>
          示例:
          Sub* mySub = dynamic_cast<Sub*>(inSuper);
          if (mySub == NULL)
         {
              //proceed to access sub methods on mySub
         }
  
   注意:如果對指針不能進行動態類型轉換,指針則為 NULL, 而不是指
   向無意義的數據。

     6.進行向上強制類型轉換時,要使用指向超類的指針或引用來避免切割問題。

     7.純虛方法與抽象基類
       (1)純虛方法: 在類定義中顯示未定義的方法。
       (2)抽象類: 含有純虛方法的類(不能實例化)。
       (3)純虛方法語法定義: 在類定義中簡單的設置方法等于 0,在 cpp 文件
          中不要編寫其實現代碼。
   示例:
   class SpreadsheetCell
   {
       public:
           SpreadsheetCell();
           virtual ~SpreadsheetCell();
           virtual void set(const std::string instring) = 0;
           virtual std::string getString() const = 0;
     };

     8.定制類型轉換函數
       (1)double 類型轉換成 string 類型
          #include <iostream>
          #include <sstream>
  
          double inValue;
          string myString;

          ostringstream ostr;
          ostr << inValue;
          myString = ostr.str();

       (2)string 類型轉換成 double 類型
          #include <iostream>
          #include <sstream>
  
          double myDouble;
          string inString;
  
          istringStream istr(inString);
          istr >> myDouble;
         if (istr.fail())
        {
           myDouble = 0;
        }

     9.使用預編譯指令避免重復包含頭文件
       #ifndef _TEST_H_
       #define _TEST_H_
       // include header files here      
       // other code omitted here

       #endif
  
十三 覆蓋方法的特殊情況
     1.在 C++ 中不能覆蓋靜態方法。
       (1)不能同時用 virtual 和 static 聲明一個方法。
       (2)在對象上可以調用 static 方法,但 static 方法只存在于類中。

十四 利用模板編寫通用代碼
     1.模板相關概念
       (1)類模板: 存儲對象的容器或數據結構。
       (2)模板的語法:
          template <typename T>
         class Grid
         {
             public:
                 Grid(int inWidth, int inHeight);
                 Grid(const Grid<T>& src);
                 Grid<T>& operator=(const Grid<T>& rhs);
                 T& getElementAt(int x, int y);
                 const T& getElementAt(int x, int y);
                 void setElementAt(int x, int y, const T& inElem);

             protected:
                 void copyFrom(const Grid<T>& src);
                 T** mCells;
        };
        (3)語法解釋
            template <typename T> : 指在類型 T 上定義的模板。
            Grid<T> : Grid 實際上是模板名。
            Grid<T> : 將作為類模板中的類名。

 (4)模板定義(實現)
    template <typename T>
    Grid<T>::Grid(int inWidth, int inHeight)
    {
        mCells = new T* [mWidth];
        for (int i = 0; i < mWidth; i++)
        {
            mCells[i] = new T[mHeight];
        }
    }

 (5)模板實例化
    Grid<int> myIntGrid;

十五 C++ 中的一些疑難問題
     1.引用
       (1)定義: 另一個變量的別名, 對引用的修改會改變其所指向的變量。
       (2)引用變量必須在創建時就初始化。
          int  x = 3;   // right
          int& xRef = x;// right
          int& emptyRef;//wrong
          注: 類的引用數據成員可在構造函數的初始化列表中初始化。

       (3)不能創建指向未命名值的引用(const 常量值除外)
          int& unnameRef = 5;      //does not compile
          const int& unnameRef = 5;//works as expect

       (4)修改引用: 引用總是指向初始化時指定的那個變量。
          int x = 3, y = 4;
          int& xRef = x;
          xRef = y; // change x value to 4, doesn't make refer to y;
          xRef = &y; // doesn't compile, type not match
         注: 引用指向的變量在初始化之后不能再改變, 只能改變此變量的值

       (5)指針引用和引用指針
          //指針引用示例(指向指針的引用)
          int*  intP;
          int*& ptrRef = intP;
          ptrRef = new int;
         *ptrRef = 5;

         注:不能聲明指向引用的引用, 也不能聲明引用指針(指向引用的指針)
         int x = 3;
         int& xRef = x;
         int&& xDoubleRef = xRef; // not compile
         int&* refPtr = &xRef; // not compile
  
       (6)傳引用vs傳值
          1)效率。復制大對象和結構要花費很長時間。
          2)正確性。不是所有的對象都允許傳值或正確的支持深復制。
          3)不想修改原對象,又利用以上兩優點,可在參數前加 const。
         4)對簡單內置類型(如int或double)要傳值,其它所有情況可傳引用。

       (7)引用vs指針
          1)引用讓程序清晰,易于理解。
          2)引用比指針安全,不存在無效的引用,不需要明確解除引用。
          3)除非需要動態分配內存或在其它地方要改變或釋放指針指向的值,否則都應使用引用而非指針。
    
     2.疑難字 const
       (1)const 變量
          使用 const 來聲明變量,對不能對其修改,以保護變量。

       (2)const 指針
       //不能改變指針指向的值
          const int* ip;
          ip = new int[10];
          ip[4] = 5; // not compile
        或
          int const* ip;
          ip = new int[10];
          ip[4] = 5; // not compile
 
          //不能改變指針自身
          int* const ip;
          ip = new int[10]; // not compile
          ip[4] = 5;

         //既不能改變指針也不能改變指針指向的值
         const int* const ip = NULL;(無用的指針)
          注: const 可以放在類型前也可以放在類型后
  
       (3)const 應用規則
          const 應用于其左則的第一項。

       (4)把對象參數傳遞時,默認的做法是把傳遞 const 引用。

       (5)const 方法
          用 const 標識類方法,可以防止方法修改類中不可變的數據成員。

     3.關鍵字 static
       (1)關于連接: C++ 中的每個源文件是獨立編譯的,得到的對象連接在一
          起。

       (2)外部連接: 一個源文件中每個名字(如函數或全局變量)對其它源文件
          是可用的。

       (3)內部連接: 一個源文件中每個名字(如函數或全局變量)對其它源文件
          是不可用的。內部連接也叫靜態連接。

       (4)函數和全局變量默認是外部連接。

       (5)聲明前加 static 可指定為內部連接。

     4.關鍵字 extern
       (1)作用: 與 static 相對,用來為位于它前面的名字聲明外部連接。
       (2)extern 用法
          // AnotherFile.cpp
         extern int x; // 只是聲明 x 為外部連接而不分配內存
         int x = 3;    //顯示定義以分配內存
        或
          extern int x = 3;//聲明和定義一起完成

          //FirstFile.cpp
         extern int x;
         cout << x << endl;

      5.強制類型轉換
      (1)const_cast<type> 去除變量的常量性。
      示例:
      void g(char* str)
      {
          // body omitted here
      }
      void f(const char* str)
      {
          g(const_cast<char*>(str));
          // other code omitted here
      }      

 (2)static_cast<type> 顯示的完成 C++ 語言支持的轉換。
    示例:
    int x = 3;
    double result = static_cast<double>(i) /10;

    注: static_cast 進行類型轉換時并不完成運行時類型檢查。

 (3)dynamic_cast<type>
    1)對類型強制轉換完成運行時類型檢查。
    2)對指針轉換失敗時會返回 NULL。
    3)對引用轉換失敗時會拋出 bad_cast 異常。

 
6.函數指針
        (1)定義: 把函數地址作為參數,可以像變量一樣使用。
        (2)定義函數指針: typedef bool(*YesNoFcn) (int, int);
        (3)用法示例

           //定義函數指針類型
           typedef string(*YesNoFcn)(int, int);

           void test(int value1, int values2, YesNoFcn isFunction)
          {
             cout << isFunction(value1, value2);
          }

         string intEqual(int intItem1, int intItem2)
         {
            return (intItem1 == intItem2) ? "match" : "not match";
         }

         //使用函數指針
          test(1, 1, &intEqual);

         注: & 是可選的


十六 C++ 中的 I/O 操作
     1.使用流
       (1)每個輸入流都有一個相關聯的源,每個輸出流都有一個相關聯的目的。

       (2)cout 和 cin 都是在 C++ 的 std 命名空間中預定義的流實例。

       (3)流的三種類型:
          1)控制臺輸入輸出流。
          2)文件流。
          3)字符串流。

       (4)輸出流
          1)輸出流在頭文件 <ostream> 中定義,輸入流在 <istream> 中定義<iosream> 中定義了輸入輸出流。

          2)cout 和 cin 指控制臺輸入輸出流。

          3)<< 操作符是使用輸出流的最簡單的方法。

          4)流其它的輸出方法
             1)put() 和 wirte()
             2)flush() 刷新輸出
 
          5)處理輸出錯誤
             1)cout.good()  流是否處于正常的可用狀態。
             2)cout.bad()   流輸出是否發生了錯誤。
             3)cout.fail()  如果最近的操作失敗則返回 true
             4)cout.clear() 重置流的錯誤狀態

   6)輸出控制符
     1)endl         輸出回車并刷新其緩沖區
     2)hex oct dec  以十六/八/十進制輸出
     3)setw         設置輸出數值數據時的字段占位符
     4)setfill    設置填充空位的占位符

       (5)輸入流
          1)>> 輸入流操作符
          2)輸入方法
              1)get()    僅僅返回流中的下一個字符
              2)unget()    引起流回退一個位置
              3)peek()    預覽下一個值
              4)getline()    從輸入流中取一行數據

          3)處理輸入錯誤
             1)good()
             2)eof()

       (6)字符串流
          1)<ssteam>    定義了字符串流的頭文件
         2)ostringstream  字符串輸出流
         3)istringstream  字符串輸入流

       (7)文件流
          1)<fstream>      定義了文件流的頭文件
          2)ifstream    文件輸入流
          3)ofstream    文件輸出流
          4)seek()    定位流的位置
          5)tell()    查詢流當前的位置

       (8)鏈接流
          1)定義: 在任何輸入流與輸出流之間建立連接,一旦訪問就刷新輸出。
          2)實現: 用輸入流的 tie() 方法
          3)示例
            #include <iostream>
           #inlcude <fstream>
           #include <string>

           main()
           {           
                ifstream inFile("input.txt");
               ofstream outFile("output.txt");
    
                //set up a link between inFile and outFile.
                inFile.tie(&outFile);

               string nextToken;
               inFile >> nextToken;
         }


十七 C++ 中的異常
     1.拋出和捕獲異常
       (1)<exception> 定義異常類的頭文件。
       (2)拋出異常對象 throw exception()
       (3)向量的使用(整型)
        vector<int> myInts;
        for (int i = 0; i < 10; i++)
        {
             myInts.push_back(i);// 增加元素
             cout << myInts[i];
        }

       (4)string 風格的字符串轉換成 C 風格的字符串
          string myString = "string style string";
          char* cStyleStrng = myString.c_str();

       (5)捕獲運行時異常
          try
         {
            ...
          }
          catch (const runtime_error& e)
         {
           ...
         }

       (6)拋出和捕獲無效參數異常
          throw invalid_argument("");

         try
          {
            ...
          }
          catch (const invalid_argument& e)
          {
             ...
          }

         注: runtime_error 和 invalid_argument 定義在頭文件<stdexcept> 中

       (7)匹配任何異常(...)
          try
          {
            // code omitted here
          }
          catch (...)
          {
            // code omitted
          }
         注: 不建議使用這種方式

       (8)使用拋出列表
          1)拋出列表: 一個函數或方法能拋出的異常列表
          2)必須為函數聲明和實現都提供拋出列表
          3)沒有拋出列表就可以拋出任何異常
         4)空的拋出列表不允許拋出任何異常

       (9)在覆蓋方法中修改參數列表
          1)從列表中刪除異常
          2)增加超類拋出列表中異常的子類
          3)不能完全刪除拋出列表

       (10)顯示異常消息
           可調用 exception 或子類的 what() 方法顯示捕獲到的異常消息
           示例:
           try
           {
               ...
           }
           catch (const exception& e)
           {
               cerr << e.what() << endl;
               exit(1);
           }
            
       (11)多態地捕獲異常
           1)在多態地捕獲異常時,要確保按引用捕獲異常。如果按值捕獲異常,就會遇到切割問題,丟失對象的信息。

           2)按引用捕獲異常可以避免不必要的復制開銷

       (12)如果異常處理不夠仔細,就會導致內存和資源泄漏
           示例
           func ()
          {
            string str1;
            string* str2 = new string();
            throw exception();
            delete str2;     // 內存泄漏
          }

       (13)使用智能指針防止內存泄漏
           #include <memory> // 定義智能指針的頭文件
           using namespace std;
           func ()
           {
               string str1;

               // 智能指針,不用自己手動釋放
              auto_ptr<string> str2(new string("hello"));
              throw exception();
           }

       (14)處理內存分配錯誤
           1)new 和 new [] 分配內存失敗默認拋出 bad_alloc 異常
           2)可用 try/catch 捕獲異常處理內存分配失敗
           3)示例:
             try
             {
                 ptr = new int[numInts];
             }
             catch (bad_alloc& e)
            {
              cerr << "Unable to alloc memory!" << endl;
              return ;
            }
         或
          1)用 new(nothrow) 在內存分配失敗時返回 NULL 來處理
          2)示例:
             ptr = new(nothrow) int[numInts];
            if (ptr == NULL)
            {
               cerr << "Unable to alloc memory!" << endl;
               return;
            }
         或
           1)用 set_new_handler() 回調函數定制分配失敗時的行為
           2)示例
              void myNewHandler()
             {
                cerr << "Unable to allocate memory!" << endl;
                abort(); // 終止程序 <cstdlib>
             }
            
             #include <new>
            #include <cstdlib>
            #include <iostream>
            using namespace std;
     
            int main(int argc, char** argv)
           {
               new_handler oldHandler = set_new_handler(myNewHandler);

              // code omitted here

             set_new_handler(oldHandler);
             return (0);
         }

posted on 2007-08-20 16:15 Normandy 閱讀(974) 評論(1)  編輯 收藏 引用 所屬分類: Programming

評論

# re: C++ 學習筆記  回復  更多評論   

做的 professional C++這本書上的筆記吧!很好.....
2008-01-21 15:16 | LJL
青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            欧美xart系列高清| 亚洲日本成人网| 欧美mv日韩mv国产网站app| 久久久久久一区| 久久天天躁狠狠躁夜夜av| 久久国产精品一区二区三区四区| 亚洲欧美变态国产另类| 久久精品99国产精品酒店日本| 亚洲欧美在线播放| 久久天堂av综合合色| 欧美激情第三页| 国产精品久久一级| 国产一区二区三区黄| 亚洲黄一区二区三区| 亚洲视频999| 久久久久成人精品免费播放动漫| 模特精品在线| 在线视频一区二区| 久久亚洲一区二区| 国产精品久久7| 亚洲激情视频网站| 午夜宅男久久久| 欧美激情一区二区久久久| 99国产精品国产精品久久| 欧美一区二区网站| 欧美男人的天堂| 狠狠色狠狠色综合日日小说| 99视频有精品| 免费成人在线视频网站| 日韩午夜在线视频| 久久亚洲精品一区二区| 国产精品美女主播| 日韩亚洲视频在线| 老司机午夜精品| 亚洲午夜一区二区| 欧美激情精品久久久久| 欧美成人在线影院| 国产视频自拍一区| 亚洲精选91| 久久中文精品| 亚洲一区二区精品在线观看| 免费一级欧美在线大片| 国产日韩一区二区三区| 一区二区三区日韩| 亚洲国产成人久久| 性欧美在线看片a免费观看| 欧美日韩国产限制| 亚洲经典视频在线观看| 久久婷婷国产麻豆91天堂| 一区二区三区偷拍| 欧美日韩国语| 日韩亚洲视频在线| 欧美成人一区二区在线| 久久高清福利视频| 国产一区在线免费观看| 午夜精品国产更新| 亚洲综合日韩中文字幕v在线| 欧美极品一区二区三区| 1769国内精品视频在线播放| 久久午夜电影网| 久久激情视频| 红桃视频亚洲| 免费h精品视频在线播放| 久久精品国产免费| 国内在线观看一区二区三区| 久久精品国产第一区二区三区最新章节| 99精品视频免费在线观看| 欧美精品18| 中文日韩在线视频| 亚洲一区免费网站| 国产日本欧美在线观看| 亚洲欧美日本另类| 亚洲欧美日韩中文播放| 国产精自产拍久久久久久| 亚洲欧美日韩综合国产aⅴ| 在线午夜精品自拍| 国产日韩欧美一区二区三区四区| 久久精品理论片| 久久久久久久久久久成人| 亚洲国产成人久久综合| 亚洲国产合集| 国产精品二区二区三区| 欧美一区1区三区3区公司| 香蕉久久夜色| 亚洲高清av在线| 日韩视频在线观看一区二区| 欧美午夜一区二区福利视频| 欧美伊人久久久久久久久影院| 久久成人精品视频| 亚洲欧洲一区| 亚洲在线视频网站| 精品99视频| 在线视频中文亚洲| 在线视频观看日韩| 一本色道久久88综合日韩精品| 欧美高清影院| 久久综合图片| 亚洲免费黄色| 香蕉av777xxx色综合一区| 亚洲国产成人在线| 在线亚洲国产精品网站| 在线观看国产精品淫| 99国产精品99久久久久久| 黑人巨大精品欧美黑白配亚洲| 亚洲激情婷婷| 国产在线视频欧美| 99精品国产在热久久婷婷| 国产视频欧美视频| 99riav国产精品| 亚洲国产高清在线| 欧美亚洲免费| 在线一区二区三区四区五区| 久久综合九色99| 欧美亚洲在线观看| 欧美紧缚bdsm在线视频| 免费试看一区| 国产一区二区三区精品久久久| 亚洲精品久久久久久久久久久久久 | 久久综合久久88| 亚洲欧美综合国产精品一区| 麻豆精品国产91久久久久久| 欧美一区亚洲| 国产精品亚洲第一区在线暖暖韩国| 麻豆91精品| 国产一区清纯| 小处雏高清一区二区三区| 亚洲欧美日韩中文在线制服| 欧美欧美全黄| 亚洲国产精品尤物yw在线观看 | 国产九九视频一区二区三区| 亚洲黑丝在线| 亚洲美女福利视频网站| 久久精品久久99精品久久| 久久精品国产一区二区三区免费看| 欧美午夜精品久久久久久超碰| 亚洲精品你懂的| 亚洲级视频在线观看免费1级| 久久久久久尹人网香蕉| 久久伊人精品天天| 一区视频在线看| 六月婷婷一区| 亚洲国产激情| 一本久道久久综合中文字幕| 欧美片第一页| 中日韩男男gay无套| 性欧美video另类hd性玩具| 国产伦精品一区二区三区| 午夜精品国产| 久久一区二区三区国产精品| 影音先锋亚洲一区| 欧美国产先锋| 中文精品视频一区二区在线观看| 亚洲欧美日韩综合aⅴ视频| 亚洲女爱视频在线| 欧美日韩精品免费观看视频完整| 亚洲国产片色| 亚洲欧美在线一区| 国产一区二区三区av电影| 久久综合久久88| 日韩一级免费观看| 午夜精品久久久久久久| 国产亚洲精品美女| 久久最新视频| 亚洲最新中文字幕| 久久精品99久久香蕉国产色戒 | 国产欧美日韩三区| 久久久久成人精品| 亚洲日本电影在线| 欧美一级播放| 亚洲欧洲一区二区三区久久| 欧美日韩在线一区二区| 羞羞漫画18久久大片| 鲁大师成人一区二区三区| 夜夜嗨av一区二区三区| 国产午夜精品久久久久久久| 久久一区国产| 亚洲视频欧美视频| 欧美国产91| 欧美一区二区视频97| 亚洲高清久久网| 国产精品入口66mio| 蜜臀av性久久久久蜜臀aⅴ| 一区二区三区福利| 欧美国产日韩一区| 校园春色国产精品| 日韩视频在线播放| 狠狠色丁香久久婷婷综合丁香| 欧美精品一区二区三区一线天视频| 亚洲一区二区精品| 亚洲伦理网站| 欧美成人资源| 欧美中文在线观看| 一区二区三区精品国产| 亚洲国产精彩中文乱码av在线播放| 国产精品观看| 欧美久久一区| 免费日韩成人| 久久久亚洲国产天美传媒修理工| 亚洲视频播放| 亚洲精品视频在线看|