Reputation: 1886
I can not create:
shared_ptr<char> n_char = make_shared<char>(new char[size_]{});
How can I create
char* chr = new char[size_]{};
using modern pointers?
Upvotes: 10
Views: 31656
Reputation: 856
In case you want to separate declaration from definition you could use the following:
(tried to demonstrate a simple example with different pointer types and different custom deleters )
class A
{
public:
A(const char* const name_)
{
size_t len = std::strlen(name_) + 1;
//Definition
//ptr_name
this->ptr_name =
std::shared_ptr<char[]>(new char[len], [](char* p)-> void {delete[] p; });
strcpy_s(this->ptr_name.get(),len,name_);
//ptr_buffer
this->ptr_buffer =
std::shared_ptr<int[]>(new int[SIZE] {1, 2, 3, 4, 5}, std::default_delete<int[]>());
}
void Print()
{
std::cout << "Print name " << std::endl;
std::cout << this->ptr_name << '\n';
std::cout << "Print buffer " << std::endl;
for (int i=0; i< SIZE; ++i)
{
std::cout << this->ptr_buffer[i] << '\n';
}
}
private:
//Declaration
std::shared_ptr<char[]> ptr_name;
std::shared_ptr<int[]> ptr_buffer;
public:
const static size_t SIZE = 5;
};
void func(A object)
{
object.Print();
}
int main()
{
const char* str = "Hello World!";
A a(str);
func(a);
a.Print();
}
Upvotes: 0
Reputation: 1
For simple char buffer:
std::shared_ptr<char> ptr( (char*)operator new( buffer_size_here ) );
Upvotes: -3
Reputation: 76286
shared_ptr n_char = make_shared(new char[size_]{});
make_shared
calls new
inside, so you never use both. In this case you only call new
, because make_shared
does not work for arrays.
However, you still need to make it call the right delete:
Before C++17:
You need to specify the deleter explicitly.
std::shared_ptr<char> ptr(new char[size_], std::default_delete<char[]>());
Since C++17:
shared_ptr
gains array support similar to what unique_ptr
already had from the beginning:
std::shared_ptr<char[]> ptr(new char[size_]);
Be aware that done this simple way you are not tracking length and in multi-threaded environment not synchronizing. If you need the buffer modifiable, making shared pointer to std::string
, or struct with std::string
and std::mutex
in it, will add a level of indirection, but will be otherwise more convenient to use.
Upvotes: 25
Reputation: 6139
You could use std::default_delete
specialized for arrays
std::shared_ptr<char> ptr(new char[size_], std::default_delete<char[]>());
See std::default_delete docs. While std::unique_ptr uses default_delete by default when no other deleter is specified and has a partial specialization that handles array types:
std::unique_ptr<char[]> ptr(new char[size_]);
With std::shared_ptr you need to select it manually by passing a deleter to the constructor.
Edit: Thanks to Jan Hudec, c++17 includes a partial specialization for array types as well:
std::shared_ptr<char[]> ptr(new char[size_]); // c++17
Upvotes: 5