Skip to content

Commit ffda672

Browse files
committed
Create example2.cpp
1 parent 8e15cf3 commit ffda672

File tree

1 file changed

+123
-0
lines changed

1 file changed

+123
-0
lines changed

example2.cpp

+123
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,123 @@
1+
#include <iostream>
2+
#include "smart_pointer_type_trait.hpp"
3+
4+
template < typename Ptr >
5+
auto get_raw_pointer( Ptr& ptr )
6+
{
7+
if constexpr ( std::is_pointer_v< Ptr > ) return ptr;
8+
else return ptr.operator->();
9+
}
10+
11+
template < typename Ty, typename Ptr >
12+
class pointer_impl
13+
{
14+
public:
15+
void reset( Ty* target = nullptr )
16+
{
17+
if constexpr ( is_smart_ptr_v< Ptr > ) impl.reset( target );
18+
else impl = target;
19+
}
20+
21+
void release() { impl = nullptr; }
22+
23+
Ty* get() noexcept { return operator->(); }
24+
const Ty* get() const noexcept { return operator->(); }
25+
26+
decltype( auto ) get_deleter() noexcept
27+
{
28+
static_assert( is_smart_ptr_v< Ptr >, "pointer_impl< Ty, Ptr >::get_deleter(): Ptr was not a smart pointer." );
29+
return impl.get_deleter();
30+
}
31+
decltype( auto ) get_deleter() const noexcept
32+
{
33+
static_assert( is_smart_ptr_v< Ptr >, "pointer_impl< Ty, Ptr >::get_deleter(): Ptr was not a smart pointer." );
34+
return impl.get_deleter();
35+
}
36+
37+
Ty& operator*() noexcept { return *impl; }
38+
const Ty& operator*() const noexcept { return *impl; }
39+
Ty* operator->() noexcept { return get_raw_pointerr( impl ); }
40+
const Ty* operator->() const noexcept { return get_raw_pointer( impl ); }
41+
operator bool() const noexcept { return static_cast< bool >( get_raw_pointer( impl ) ); }
42+
43+
// special member functions
44+
pointer_impl( Ty* impl = nullptr ) : impl{ impl } {}
45+
~pointer_impl() { impl = nullptr; }
46+
47+
private:
48+
Ptr impl;
49+
};
50+
51+
// ======================================================
52+
// ******************************************************
53+
// Decoupling by using keyword.
54+
// memory allocation policy has only-one dependancy, this code.
55+
// ======================================================
56+
template < typename Ty >
57+
using pointer = pointer_impl< Ty, std::unique_ptr< Ty > >; // can change to diffrent pointer
58+
// If you add more pointer object, ( and similar type trait )
59+
// can also change to the pointer object.
60+
// ******************************************************
61+
// ======================================================
62+
63+
template < typename Ty, typename ... Args >
64+
auto make( Args&& ... args )
65+
{
66+
return pointer< Ty >{ new Ty{ std::forward< Args >( args )... } };
67+
}
68+
69+
struct INT
70+
{
71+
INT( int impl = 0 ) : impl{ impl } { std::cout << "INT constructor called\n"; }
72+
~INT() { std::cout << "INT destructor called\n"; }
73+
INT( const INT& other ) : impl{ other.impl } { std::cout << "INT copy constructor called\n"; }
74+
INT& operator=( const INT& other )
75+
{
76+
if ( this != &other )
77+
{
78+
std::cout << "INT copy allocator called\n";
79+
impl = other.impl;
80+
}
81+
82+
return *this;
83+
}
84+
INT( INT&& other ) : impl{ other.impl } { std::cout << "INT move constructor called\n"; }
85+
INT& operator=( INT&& other )
86+
{
87+
if ( this != &other )
88+
{
89+
std::cout << "INT move allocator called\n";
90+
impl = other.impl;
91+
}
92+
93+
return *this;
94+
}
95+
operator int() { return impl; }
96+
97+
int impl;
98+
};
99+
100+
int main()
101+
{
102+
std::cout << "must call constructor ==================\n";
103+
auto a = make< INT >( 4 );
104+
std::cout << "========================================\n\n\n";
105+
106+
std::cout << "get_deleter() call =====================\n";
107+
std::cout << typeid( a.get_deleter() ).name() << '\n';
108+
std::cout << "========================================\n\n\n";
109+
110+
std::cout << "print value ============================\n";
111+
std::cout << "value: " << *a << '\n';
112+
std::cout << "========================================\n\n\n";
113+
114+
std::cout << "must call constructor and destructor ===\n";
115+
a.reset( new INT{ 5 } );
116+
std::cout << "========================================\n\n\n";
117+
118+
std::cout << "print value ============================\n";
119+
std::cout << "value: " << *a << '\n';
120+
std::cout << "========================================\n\n\n";
121+
122+
std::cout << "must call destructor ===================\n";
123+
}

0 commit comments

Comments
 (0)