Search code examples
c++c-stringsc-str

Using String's c_str() and assigning to char const*: assignment of read-only location


My problem is this: I have a constant pointer to a constant char pointer (2D char array where both dimensions are const). I need to assign C-strings to this array. I have a std::vector of std::strings which I used c_str() on to create a vector of c_strings. Now I'm assigning those C-string pointers to this array, but I'm getting

src/rshell.cpp:45:44: error: assignment of read-only location ‘*(c_arr 
((sizetype)(((long unsigned int)i) * 8ul)))’
for (int i = 0; i < size1; i++) c_arr[i] = commands.at(i);

Here's the code with the error

/* Confusing as heck, let me explain!
 * char const* means pointer to a constant char
 * so char const* const means a const pointer to a const char
 * and char const* const* means a const pointer to a const char pointer!
 * (Read declarations from right to left to make it make sense -
 *  char const* = POINTER (*) to a CONST CHAR)
 */
char const* const* c_arr = new char*[size1];
for (int i = 0; i < size1; i++)
  c_arr[i] = commands.at(i); // line 38

And here's the vector of string to C-string part if it helps.

for (tokenizer::iterator it = parse.begin(); it != parse.end(); it++)
  words.push_back(*it);

vector<const char*> commands;
// add string to c_string equiv return vector
for (vector<string>::iterator it = words.begin(); it != words.end(); it++) {
    commands.push_back(it->c_str());
}

Solution

  • Since commands is a std::vector<const char *>, the expression &commands[0] will yield a const char ** (also known as char const **) which you can happily assign to a char const * const *. So unless you really need a copy, you could go with

    char const * const *c_arr = &commands[0];
    

    Note that this means that c_arr is really only useful as long as commands exists (which in turn is really only useful as long as the std::string objects in words exist).