How will std::spanstream usually be used in C++? - c++

<spanstream> will debut in C++23 (see cppreference). According to the proposal, they are string-streams with std::span based buffers.
My questions are:
Does std::spanstream have somewhat equivalent uses of the old std::strstream (or strstream deprecated in C++ 98)?
What will be the benefits of using them after the full release of C++ 23?

They are intended to be a near drop-in replacement for strstream (except with proper bounds checking). As such, they will have the exact same use cases. When you have an existing buffer that you want to stream into/outof.
The ability to move a std::string into stringstreams added in C++20 eliminated the use case when the existing buffer is in a std::string. But sometimes you just have a naked char const* with a known length.

Related

Will we have a size_t strlen(const char8_t*) in a future C++ version

char8_t in C++20 fixes some problems of char, so I was considering using char8_t instead of char for utf8 text (e.g. text from command line). But then I noticed that strlen was not specified in the standard to be used with char8_t, actually none of the functions in the cstring library are. Can I expect this to happen in a next standard update? Or is char8_t never intended to replace char in the way I had in mind?
I'm the author of the P0482 and P1423 char8_t proposals.
The intent of those proposals was to introduce the char8_t type with the same level of support present for char16_t and char32_t and then to follow up with additional functionality later. These proposals were adopted late in the C++20 development cycle (at the San Diego and Cologne meetings respectively), so there wasn't opportunity to deliver additional features for C++20.
One of the directives for SG16 as described in P1238 is to standardize new encoding aware text container and view types. Work is progressing in this area and we hope to deliver it for C++23. It is hoped that these new containers and views will supplant much raw string handling in C++.
With regard to strlen specifically, strlen is a C API. N2231 is a proposal to add char8_t support to C (again, at the same level as the existing support for char16_t and char32_t). That proposal has not yet been accepted by WG14. Assuming it is eventually accepted, then it would make sense to follow up with additional char8_t-based C string management functions (perhaps enhancing support for char16_t and char32_t as well).
At present, I'm working on completing an implementation of N2231 in gcc and glibc. Once that is complete, I intend to submit a revision of N2231 to WG14.
You can help! SG16 is an open group. Please feel free to subscribe to our mailing list, join us on Slack, share your ideas, needs, and wants, and write proposals for new functionality (we can help with how to do that).
These new char types are intended to use C++ string template std::basic_string, namely to define std::u8string. So the best in your case is use C++ strings.
As for the future support of char8_t in cstring library, I suppose this question is more suitable to the future C standard. I'm afraid, it will not be an easy and will be unlikely update, since C does not have overloaded functions, and this update will require new functions like c8slen in addition to strlen and wcslen.
char8_t is intended for UTF-8-encoded strings. As such, APIs that consume them will be assumed by users to be Unicode aware on some level. Quite a lot of the contents of the <cstring> header would be inappropriate for char8_t, as their behavior is very much not in line with Unicode (would strcmp do proper Unicode collation?).
If you want access to functions that work similarly to the <cstring> functions, then you'll find std::char_trait<char8_t> to contain some useful ones, in particular length (exactly like strlen) and compare (explicitly lexicographical). Most of the rest of <cstring> can be handled adequately through C++ algorithms.
0 can still act as null-terminator in utf8-strings, so technically nothing prevents you (except a lack of appropriate function) from using strlen to count the amount of bytes(!) in utf8 sequence. If you want to find the number of chars you would need a separate function.

Is strcpy equivalent to strcpy_s

I would like to know if I can safely replace strcpy_s defined here https://msdn.microsoft.com/en-us/library/td1esda9.aspx - (the one with two arguments) with strcpy defined here http://en.cppreference.com/w/c/string/byte/strcpy - (the first one). If no then what is the closest version of strcpy that I can use to replace strcpy_s?
The C11 standard added bounds-checked functions including strcpy_s(). So if you're worried about portability, it's okay as long as you have a C11-compliant compiler. Note that C11-standard "constraint handler" is slightly different than the Microsoft CRT's "invalid parameter handler" so if you're installing a custom handler, it may need some adjustments.
As for replacing it altogether, no, you can't safely replace it with strcpy() for reasons that should be obvious: strcpy() is not bounds-checked. You would either need to do your own bounds checking using strlen(), or use strncpy(), but note that strncpy() behaves differently (specifically, if the source string is too big to fit in the destination, the destination buffer will not be null-terminated).

Can I use a C Variable Length Array in C++03 and C++11?

C has a really cool feature called variable length arrays. Its available in C90 and above, and it allows deferring the size of the array until runtime. See GCC's manual 6.19 Arrays of Variable Length.
I'm working in C++. At std=c++11, I'm catching a compile failure due to the use of alloca under Cygwin. I want to switch to variable length arrays, if possible. I also want to try and avoid std::vector and std::array because I want to stay out of the memory manager. I believe every little bit helps, so I'm happy to take these opportunities (that some folks consider peepholes).
Can I use a variable length array in C++03 and C++11?
VLAs are not in standard C++03 or C++11, so you'll better avoid them if you want to write strictly standard conforming code (and use e.g. std::vector, which generally use heap for its data - but you might use your own allocator...).
However, several C++ compilers (recent GCC & Clang) are accepting VLAs as an extension.
It is the same for flexible array members; they are not standard in C++ (only in C) but some compilers accept them.
dynarray-s did not get into the C++11 standard...
Not if you want code that is standard C++.
No C++ standard supports VLAs, but some C++ compilers do as a vendor-specific extension.
You can achieve a similar effect in C++ using the standard vector. Note that, unlike VLAs which can only be sized when created, a standard vector can be resized as needed (subject to performing appropriate operations on it).

Length of a C string: std::strlen() vs. std::char_traits<char>::length()

Both are equivalent in that they return the length of the null-terminated character sequence. Are there reasons of preferring one to the other?
Use the simpler alternative. std::char_traits::length is great and all, but for C strings it does the same and is much longer code.
Do yourself a favour and avoid code bloat. I’m a huge fan of C++ functions over C equivalent (e.g. I will never use std::strcpy or std::memcpy, there’s a perfectly fine std::copy). But avoiding std::strlen is just silly.
One reason to use C++ functions exclusively is interface uniformity: for instance, both std::strcpy and std::memcpy have atrocious interfaces. However, std::strlen is a perfectly fine algorithm in the best tradition of C++. It doesn’t generalise, true, but the neither do other class-specific free functions found in the standard library.
std::strlen() is a holdover from the C Standard Library and only operates on a const char* (it is unsafe in that it has undefined behavior if the string is not null terminated). If the string is using a wide character set (e.g. const unsigned short*), std::strlen() is useless.
std::char_traits<T>::length() will operate on whatever the T type is (e.g. if it is an unsigned short, it will still operate properly, but also requires a null terminated value - that is the last value must be T(0) - if an array of T's passed to it is not null terminated, behavior is undefined as well).
In general, when dealing with strings, it is better to use std::string::length() instead of using C-style character strings.
Both Zack Howland and Konrad Rudolph have a point. Thanks. I accept both answers. The summarized reply would be:
There doesn't seem to be any except personal preference either for shorter code or the C++ standard library (I leave out generalization since it wasn't the point of the question as can be seen from the title).
std::strlen() is a C standard library compatibility (even though it is part of ISO C++) function that takes const char* as an argument. length() is a method of the std::string family of classes. So if you want to use strlen() on std::string you'd have to write:
strlen(mystring.c_str())
which is less tidy than mystr.length(). Apart from that, there should be no tangible difference (for char type, that is).

Was strstream ever part of the standard?

Recently I've skimmed through n3376 and came across an interesting section in Annex D: [depr.ios.members]. It mentions the "old" IO-classes strstreambuf, istrstream, ... as deprecated.
Personally I haven't used any of these for any serious program (think I once had to use them in an assignment, but after that i stayed with <sstream>).
From what I know these classes were pre-standard, but were they ever part of any standard? If not, I don't quite understand why there are even mentioned in the standard...
Yes, they always were (since 1998) and are part of the standard, but they are deprecated (and always have been, since 1998).
The natural question that follows is: why were they added as deprecated? I can only speculate here, but there is no alternative where you can manage your own buffer, and you can not access the string of stringstream directly, so this template is without a good alternative. The committee will surely be open for a new proposal to fill this gap (that is, control the buffer), but undeprecating strstream is likely a no-no.