Introduce a variant of rtc::split that returns a vector of string_view

Intended to be compatible with absl::StrSplit, but without the binary
cost of that dependency.

Bug: webrtc:13579
Change-Id: I167726903d74b8d5f299886cfb3e5d60610ddb93
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/247185
Reviewed-by: Ali Tofigh <alito@webrtc.org>
Reviewed-by: Harald Alvestrand <hta@webrtc.org>
Commit-Queue: Niels Moller <nisse@webrtc.org>
Cr-Commit-Position: refs/heads/main@{#35780}
This commit is contained in:
Niels Möller
2022-01-24 14:15:03 +01:00
committed by WebRTC LUCI CQ
parent 3a88dd99c7
commit 2d3186e001
6 changed files with 31 additions and 17 deletions

View File

@ -210,6 +210,7 @@ rtc_source_set("simulcast_description") {
"../rtc_base:socket_address",
"../rtc_base/system:rtc_export",
]
absl_deps = [ "//third_party/abseil-cpp/absl/strings" ]
}
rtc_source_set("rtc_pc") {

View File

@ -101,33 +101,33 @@ rtc::StringBuilder& operator<<(rtc::StringBuilder& builder,
// sc-id = [sc-id-paused] rid-id
// rid-id = 1*(alpha-numeric / "-" / "_") ; see: I-D.ietf-mmusic-rid
RTCErrorOr<SimulcastLayerList> ParseSimulcastLayerList(const std::string& str) {
std::vector<std::string> tokens;
rtc::split(str, kDelimiterSemicolonChar, &tokens);
std::vector<absl::string_view> tokens =
rtc::split(str, kDelimiterSemicolonChar);
if (tokens.empty()) {
return ParseError("Layer list cannot be empty.");
}
SimulcastLayerList result;
for (const std::string& token : tokens) {
for (const absl::string_view& token : tokens) {
if (token.empty()) {
return ParseError("Simulcast alternative layer list is empty.");
}
std::vector<std::string> rid_tokens;
rtc::split(token, kDelimiterCommaChar, &rid_tokens);
std::vector<absl::string_view> rid_tokens =
rtc::split(token, kDelimiterCommaChar);
if (rid_tokens.empty()) {
return ParseError("Simulcast alternative layer list is malformed.");
}
std::vector<SimulcastLayer> layers;
for (const std::string& rid_token : rid_tokens) {
for (const absl::string_view& rid_token : rid_tokens) {
if (rid_token.empty() || rid_token == kSimulcastPausedStream) {
return ParseError("Rid must not be empty.");
}
bool paused = rid_token[0] == kSimulcastPausedStreamChar;
std::string rid = paused ? rid_token.substr(1) : rid_token;
absl::string_view rid = paused ? rid_token.substr(1) : rid_token;
layers.push_back(SimulcastLayer(rid, paused));
}

View File

@ -14,7 +14,7 @@
namespace cricket {
SimulcastLayer::SimulcastLayer(const std::string& rid, bool is_paused)
SimulcastLayer::SimulcastLayer(absl::string_view rid, bool is_paused)
: rid{rid}, is_paused{is_paused} {
RTC_DCHECK(!rid.empty());
}

View File

@ -16,6 +16,8 @@
#include <string>
#include <vector>
#include "absl/strings/string_view.h"
namespace cricket {
// Describes a Simulcast Layer.
@ -23,7 +25,7 @@ namespace cricket {
// See also: https://tools.ietf.org/html/draft-ietf-mmusic-rid-15 for
// an explanation about rids.
struct SimulcastLayer final {
SimulcastLayer(const std::string& rid, bool is_paused);
SimulcastLayer(absl::string_view rid, bool is_paused);
SimulcastLayer(const SimulcastLayer& other) = default;
SimulcastLayer& operator=(const SimulcastLayer& other) = default;

View File

@ -214,19 +214,27 @@ std::string join(const std::vector<std::string>& source, char delimiter) {
return joined_string;
}
std::vector<absl::string_view> split(absl::string_view source, char delimiter) {
std::vector<absl::string_view> fields;
size_t last = 0;
for (size_t i = 0; i < source.length(); ++i) {
if (source[i] == delimiter) {
fields.push_back(source.substr(last, i - last));
last = i + 1;
}
}
fields.push_back(source.substr(last));
return fields;
}
size_t split(absl::string_view source,
char delimiter,
std::vector<std::string>* fields) {
RTC_DCHECK(fields);
fields->clear();
size_t last = 0;
for (size_t i = 0; i < source.length(); ++i) {
if (source[i] == delimiter) {
fields->emplace_back(source.substr(last, i - last));
last = i + 1;
}
for (const absl::string_view field_view : split(source, delimiter)) {
fields->emplace_back(field_view);
}
fields->emplace_back(source.substr(last));
return fields->size();
}

View File

@ -62,7 +62,10 @@ size_t hex_decode_with_delimiter(char* buffer,
std::string join(const std::vector<std::string>& source, char delimiter);
// Splits the source string into multiple fields separated by delimiter,
// with duplicates of delimiter creating empty fields.
// with duplicates of delimiter creating empty fields. Empty input produces a
// single, empty, field.
std::vector<absl::string_view> split(absl::string_view source, char delimiter);
size_t split(absl::string_view source,
char delimiter,
std::vector<std::string>* fields);