63

I am using a library which accepts data as a vector of chars. I need to pass a string to the library.

I think about using std::vector constructor which accepts iterators to carry out the conversion - but wondered if there is a better way of doing it?

/*Note: json_str is of type std::string*/
const std::vector<char> charvect(json_str.begin(), json_str.end()); 
1
  • 3
    Are you just curious, or did you actually measure and determine that a significant part of your program is spent on copying strings? Commented Nov 23, 2011 at 19:29

4 Answers 4

41

Nope, that's the way to do it, directly initializing the vector with the data from the string.

As @ildjarn points out in his comment, if for whatever reason your data buffer needs to be null-terminated, you need to explicitly add it with charvect.push_back('\0').

Also note, if you want to reuse the buffer, use the assign member function which takes iterators.

Sign up to request clarification or add additional context in comments.

5 Comments

Note that if the data needs to be null-terminated, the terminating null will have to be pushed back manually.
@ildjarn: Good point. However, it would be strange for a data buffer to be null terminated, but you never know...
Note that since C++11 std::string is forced to use null terminated strings in its internal buffer. So that push_back is no longer necessary.
@Manu343726: It still is. Just because it's mandated to be internally null-terminated doesn't change the fact that the '\0' is not part of the string elements. If you iterate over the string, you won't get a '\0'.
I concur about using the vector member function assign for setting a new value. In general, it is best to make use of provided member functions of a class since library developers have the opportunity of optimizing the implementation with the class in mind.
19

Your method of populating the vector is fine -- in fact, it's probably best in most cases.

Just so that you know however, it's not the only way. You could also simply copy the contents of the string in to the vector<char>. This is going to be most useful when you either have a vector already instantiated, or if you want to append more data to the end -- or at any point, really.

Example, where s is a std::string and v is a std::vector<char>:

std::copy( s.begin(), s.end(), std::back_inserter(v));

As with the constructor case, if you need a null-terminator then you'll need to push that back yourself:

v.push_back('\0');

Comments

3

You can do it in this way.

  std::string s = "Hello World!";
    std::vector<char> v(s.begin(), s.end());
    for (const char &c: v)
        std::cout << c;

Comments

0

An alternative that might be worth considering if you need the terminating null is:

std::vector<char> charvect(json_str.c_str(), json_str.c_str() + json_str.size() + 1); 

and if charvect already exists you can do:

charvect.assign(json_str.c_str(), json_str.c_str() + json_str.size() + 1);

This might be quicker than doing a push_back('\0') particularly if the push_back triggers a memory reallocation.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.