How to convert a std::string to const char* or char*?
如何将std::string
转换为char*
或const char*
?
If you just want to pass a std::string
to a function that needs const char*
you can use
std::string str;
const char * c = str.c_str();
If you want to get a writable copy, like char *
, you can do that with this:
std::string str;
char * writable = new char[str.size() + 1];
std::copy(str.begin(), str.end(), writable);
writable[str.size()] = ' '; // don't forget the terminating 0
// don't forget to free the string after finished using it
delete[] writable;
Edit : Notice that the above is not exception safe. If anything between the new
call and the delete
call throws, you will leak memory, as nothing will call delete
for you automatically. There are two immediate ways to solve this.
boost::scoped_array
boost::scoped_array
will delete the memory for you upon going out of scope:
std::string str;
boost::scoped_array<char> writable(new char[str.size() + 1]);
std::copy(str.begin(), str.end(), writable.get());
writable[str.size()] = ' '; // don't forget the terminating 0
// get the char* using writable.get()
// memory is automatically freed if the smart pointer goes
// out of scope
std::vector
This is the standard way (does not require any external library). You use std::vector
, which completely manages the memory for you.
std::string str;
std::vector<char> writable(str.begin(), str.end());
writable.push_back(' ');
// get the char* using &writable[0] or &*writable.begin()
Given say...
std::string x = "hello";
Getting a `char *` or `const char*` from a `string`
How to get a character pointer that's valid while x
remains in scope and isn't modified further
C++11 simplifies things; the following all give access to the same internal string buffer:
const char* p_c_str = x.c_str();
const char* p_data = x.data();
const char* p_x0 = &x[0];
char* p_x0_rw = &x[0]; // compiles iff x is not const...
All the above pointers will hold the same value - the address of the first character in the buffer. Even an empty string has a "first character in the buffer", because C++11 guarantees to always keep an extra NUL/0 terminator character after the explicitly assigned string content (eg std::string("this that", 9)
will have a buffer holding "this that "
).
Given any of the above pointers:
char c = p[n]; // valid for n <= x.size()
// i.e. you can safely read the NUL at p[x.size()]
Only for the non- const
pointer from &x[0]
:
p_x0_rw[n] = c; // valid for n <= x.size() - 1
// i.e. don't overwrite the implementation maintained NUL
Writing a NUL elsewhere in the string does not change the string
's size()
; string
's are allowed to contain any number of NULs - they are given no special treatment by std::string
(same in C++03).
In C++03 , things were considerably more complicated (key differences highlighted ):
x.data()
const char*
to the string's internal buffer which wasn't required by the Standard to conclude with a NUL (ie might be ['h', 'e', 'l', 'l', 'o']
followed by uninitialised or garbage values, with accidental accesses thereto having undefined behaviour). x.size()
characters are safe to read, ie x[0]
through x[x.size() - 1]
&x[0]
f(const char* p, size_t n) { if (n == 0) return; ...whatever... }
f(const char* p, size_t n) { if (n == 0) return; ...whatever... }
you mustn't call f(&x[0], x.size());
when x.empty()
- just use f(x.data(), ...)
. x.data()
but: const
x
this yields a non- const
char*
pointer; you can overwrite string content x.c_str()
const char*
to an ASCIIZ (NUL-terminated) representation of the value (ie ['h', 'e', 'l', 'l', 'o', '