程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> 關於C語言 >> Spear Parser(一):智能指針類

Spear Parser(一):智能指針類

編輯:關於C語言

Spear Parser簡介

Spear Parser(以下簡稱Spear)包含了Collins Model 1的訓練部分,對於理解和實現Collins模型來說,是個很好的入門代碼。因為M Collins的thesis中提供的代碼只包含了Parsing的部分,並沒有Training的部分,所以直接看Parsing的代碼,理解起來可能有點費勁。而Dan Bikel的貌似有點龐大,對於入門來說,沒必要看得那麼復雜。所以,我就本著偷懶的原則,到處Google Collins Model的實現,找到了一個還算不錯的Spear.

Spear的介紹網址The Spear Parser,它是open-source的。

為了更好地理解Spear,記錄學習進度,做個系列的學習筆記吧。看的時候是從上往下看的,記的時候就從下往上記,先講講一些周邊的類,最後講講整體的實現思路。

這個部分講的是Spear的一些輔助類,第一個就是智能指針類(Smart Pointer)。

智能指針類簡介

智能指針是C++中一種常用的技術,主要用來防止一個指針指向一個不存在的對象,核心是控制一個對象的刪除時機。具體介紹可以參考《C++ Primer》中的介紹,第四版中文版是在13.5.1的部分。

Spear中智能指針類的實現 

Spear中智能指針類的實現,主要有兩個類,RCObject和RCIPtr。RCIPtr是一個具體智能指針的實現類,RCObject是它能夠指向的所有對象的父類。RCObject其實就是封裝了count的管理行為,以便RCIPtr能夠使用use-count技術實現Smart Pointer。

RCObject的代碼如下:

  1. class RCObject  
  2.  public: 
  3.   void addReference(); 
  4.   void removeReference(); 
  5.  protected: 
  6.   RCObject(); 
  7.   RCObject(const RCObject& rhs); 
  8.   RCObject& operator=(const RCObject& rhs); 
  9.   virtual ~RCObject() = 0; 
  10.  public: 
  11.   unsigned short refCount; 
  12. }; 
  13. inline RCObject::RCObject() 
  14.   : refCount(0){} // std::cout << "RCObject constr\n"; } 
  15. inline RCObject::RCObject(const RCObject&) 
  16.   : refCount(0){} // std::cout << "RCObject copy constr\n"; } 
  17. inline RCObject& RCObject::operator=(const RCObject&) 
  18.   return *this; 
  19. }   
  20. inline RCObject::~RCObject() {} 
  21. inline void RCObject::addReference()  
  22.   ++refCount; 
  23. inline void RCObject::removeReference() 
  24.   if (--refCount == 0) delete this; 

這段代碼挺簡單的,就是普通的構造,拷貝構造,賦值,析構,外加對refCount的操作。注意點就是removeReference時當refCount為0的時候就把當前的對象刪除了,這個其實就是一個的Smart Pointer的實現思路。後續可以看到很多的類都繼承RCObject,以便於能夠用智能指針技術管理指向它們對象的指針。

RCIPtr是Smart Pointer的實現,主要就是拷貝構造,賦值運算符,析構函數的實現。同時,它還重載了各種==,!=的實現,但這些重載並不是重點。

RCIPrt的代碼如下:

  1. template<class T> 
  2. class RCIPtr  
  3.  public: 
  4.   explicit RCIPtr(T* realPtr = 0); 
  5.   RCIPtr(const RCIPtr& rhs); 
  6.   ~RCIPtr(); 
  7.   RCIPtr& operator=(const RCIPtr& rhs); 
  8.   T* operator->() const; 
  9.   T& operator*() const; 
  10.   void clear() { 
  11.     *this = RCIPtr<T>(0); 
  12.   }; 
  13. private: 
  14.   T *pointee; 
  15.   void init() { 
  16.     if(pointee != 0) pointee->addReference(); 
  17.   } 
  18. }; 

核心代碼的實現:

  1. template<class T> 
  2. RCIPtr<T>::RCIPtr(T* realPtr) 
  3.   : pointee(realPtr) 
  4. {  
  5.   init(); 
  6. template<class T> 
  7. RCIPtr<T>::RCIPtr(const RCIPtr& rhs) 
  8.   : pointee(rhs.pointee) 
  9. {  
  10.   init();  
  11. template<class T> 
  12. RCIPtr<T>::~RCIPtr() 
  13. {  
  14.   if(pointee != 0) pointee->removeReference();  
  15. template<class T> 
  16. RCIPtr<T>& RCIPtr<T>::operator=(const RCIPtr& rhs) 
  17.   if (pointee != rhs.pointee) {          
  18.     if(pointee != 0) pointee->removeReference();      
  19.     pointee = rhs.pointee; 
  20.     init(); 
  21.   } 
  22.   return *this; 

Spear 智能指針類的使用

RCIPtr<BankEdge> _head; 這個就可以看作:BankEdge * _head, 用法基本一樣 _head-&gt;,*_head都可以像原來的指針那樣用,因為都重載過了。

本文出自 “青禾” 博客,請務必保留此出處http://snowteng17.blog.51cto.com/1532294/541344

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved