2011-11-16 3 views
1

저는 오랫동안 boost::smart_ptr 라이브러리의 사용자이고 그것을 좋아합니다. 모든 부스트 라이브러리와 마찬가지로 C++ 표준 라이브러리와 잘 작동하도록 설계되었습니다. 보통 대단한 것입니다. 나는 상황에 직면하고있어 불행하게도표준 라이브러리가없는 C++ 스마트 포인터

, 나는 표준 라이브러리의 완전히 독립 할 필요가 있었다. 이것에도 불구하고 나는 boost::smart_ptr에 의해 제공되는 것과 같은 종류의 기능을 필요로 할 것이다. (분명히 std와 관련된 모든 것을 제외하고 : :). 여기에는 bool 및 -> 연산자 오버로드, week_ptrshared_ptr 등의 관계가 포함됩니다.

이 상황에 직면 한 사람이 있습니까? 나는 을 시작점으로 사용하고 std:: 관련 항목을 대체/제거하려고합니다. 그러나 복잡성을 보면서 점점 더 많은 것들을 깨뜨리는 것에 대해 우려하고 있습니다.

+1

, 왜 당신은 표준 라이브러리를 사용할 수 없습니다. 이것이 언제 요구 사항이 될지 궁금하다. – flipchart

+3

부스트 또는 표준 라이브러리와 독립적이되고 싶습니까? 표준 라이브러리가 없으면 더 이상 C++이 아닙니다. – juanchopanza

+0

나는 그 질문을 이해하지 못한다. std를 사용할 수 없거나 부스트를 사용할 수 없습니까? 아니면 둘 다 사용할 수 있습니까? – ronag

답변

2

Loki 라이브러리가 도움이 될 수 있으며 SmartPtr 클래스가 있습니다. 그것은 std (std :: swap, std :: runtime_error)를 사용하지만 그것을 없애기가 너무 어려워 보이지 않습니다.

+0

고마워, 내가 좀 봐! – jbat100

+0

고마워, 내가 찾고있는 것에 가장 가깝고, 그들이 말하는 것에 대해 알고있는 사람들이 분명히 해냈다 ... – jbat100

1

libc++에 관심이있을 수 있습니다.

이것은 자유로운 라이선스 (MIT 또는 BSD 유사)로 C++ 표준 라이브러리를 구현하여 자유롭게 물건을 선택할 수 있도록합니다.

모든 스트림 처리는 매우 복잡하며 (로캘 항목이 많음) STL 부분 (컨테이너 및 알고리즘)은 물론 숫자 항목의 일부 (서식 지정 제외)는 그대로 사용할 수 있습니다.

스트림이 필요한 경우 조금 복잡합니다.

마지막으로 가장 큰 문제는 예외 처리에서 비롯된 것일 수 있습니다. 표준 라이브러리는 일반적으로 예외 사용 (예 : std::out_of_range)으로 작동하고 예외 관리는 일반적으로 외부 라이브러리 (예 : libunwind 참조)를 기반으로합니다. 물론 자신의 라이브러리를 다시 구현했기 때문에 던지지 않고 assert을 선택할 수 있습니다.

내가 관심을 갖는 모든 장치에서 작동하도록하는 것은 큰 고통이 될 것이므로 (예외적 인 C++이긴하지만 오브젝트와 템플릿을 여전히 얻음) 예외를 사용하지 말 것을 충고합니다.

0

참조 카운트에서 고전적입니다. 일부 기본 코드는 다음과 같이 보일 것입니다 (내가 생성 할 수있는 가장 짧은 코드). 참조 계산에 대해 모르는 경우가 아니면 간단해야합니다.

template <class CL> 
struct refCount { 
    refCount() : nlinks_(1) , p_(0) {} 
    refCount(CL*p) : nlinks_(1) , p_(p) {} 
    ~refCount() { if (!nlinks_) delete p_;} 
    size_t nlinks_; 
    CL* p_; 
    }; 

template <class CL> 
class mySmartPtr { 
public: 
    mySmartPtr() : rc_(new refCount<CL>()) {} 
    mySmartPtr(CL* p) : rc_(new refCount<CL>(p)) {} 
    mySmartPtr(const mySmartPtr<CL> & otherSmartPtr) : rc_(otherSmartPtr.rc_) { rc_->nlinks_++ ;} 
    mySmartPtr & operator=(const mySmartPtr<CL> & otherSmartPtr)  { 
     otherSmartPtr.rc_->nlinks_++; 
     if (!(-- rc_->nlinks_)) delete rc_; 
     rc_ = otherSmartPtr.rc_; 
     return *this;} 
    CL& operator *() {return * rc_->p_ ; } 
    ~mySmartPtr() { if(!(--rc_->nlinks_)) delete rc_;} 
// commented to print #links (remove it) 
// protected: 
    refCount<CL> *rc_; 
     }; 

동적/정적 캐스팅 (스레드 안전성)이 필요한 경우 약간의 작업이 더 필요합니다. 사용

예 :

그냥 관심 밖으로
int main() 
{ 
mySmartPtr<int> i; 
i = mySmartPtr<int>(new int(1)); 
*i = 7; 
mySmartPtr<int> j(new int(3)); 
j = i; 
std::cout << *j << std::endl ; // prints 7 
std::cout << i.rc_->nlinks_ << std::endl ; // prints 2, i and j point to the same 
{ 
    mySmartPtr<int> k(j); 
    std::cout << i.rc_->nlinks_ << std::endl ; // prints 3, k points there two 
} 
std::cout << i.rc_->nlinks_ << std::endl ; // prints 2 , k gone out of scope 

return 0; 
} 
관련 문제