diff options
author | Boris Kolpackov <boris@codesynthesis.com> | 2024-02-19 10:34:40 +0200 |
---|---|---|
committer | Boris Kolpackov <boris@codesynthesis.com> | 2024-02-19 12:44:32 +0200 |
commit | bed6b6a9170253e010cbffd59202add4edfd1c2b (patch) | |
tree | ee33d1ad1f43bfc0966b8f85f7f84ad6272b1e71 /libbuild2/functions-string.cxx | |
parent | 70d63c266ffd313c03f6cf68e7080bbcd3c8c064 (diff) |
Add string_map buildfile value type
This exposes the std::map<std::string,std::string> type to buildfiles.
New functions:
$size(<string-map>)
$keys(<string-map>)
Subscript can be used to lookup a value by key. The result is [null] if
there is no value associated with the specified key. For example:
map = [string_map] a@1 b@2 c@3
b = ($map[b]) # 2
if ($map[z] == [null])
...
Note that append (+=) is overriding (like std::map::insert_or_assign())
while prepend (=+) is not (like std::map::insert()). In a sense, whatever
appears last (from left to right) is kept, which is consistent with what
we expect to happen when specifying the same key repeatedly in a literal
representation. For example:
map = [string_map] a@0 b@2 a@1 # a@1 b@2
map += b@0 c@3 # a@1 b@0 c@3
map =+ b@1 d@4 # a@1 b@0 c@3 d@4
Example of iteration:
map = [string_map] a@1 b@2 c@3
for p: $map
{
k = $first($p)
v = $second($p)
}
While the subscript is mapped to key lookup only, index-based access can be
implemented (with a bit of overhead) using the $keys() function:
map = [string_map] a@1 b@2 c@3
keys = $keys($m)
for i: $integer_sequence(0, $size($keys))
{
k = ($keys[$i])
v = ($map[$k])
}
Also, this commit changes the naming of other template-based value types (not
exposed as buildfile value types) to use C++ template id-like names (e.g.,
map<string,optional<bool>>).
Diffstat (limited to 'libbuild2/functions-string.cxx')
-rw-r--r-- | libbuild2/functions-string.cxx | 25 |
1 files changed, 21 insertions, 4 deletions
diff --git a/libbuild2/functions-string.cxx b/libbuild2/functions-string.cxx index 8e5a315..b332efa 100644 --- a/libbuild2/functions-string.cxx +++ b/libbuild2/functions-string.cxx @@ -119,14 +119,16 @@ namespace build2 }; // $size(<strings>) + // $size(<string-map>) // $size(<string>) // - // First form: return the number of elements in the sequence. + // First two forms: return the number of elements in the sequence. // - // Second form: return the number of characters (bytes) in the string. + // Third form: return the number of characters (bytes) in the string. // - f["size"] += [] (strings v) {return v.size ();}; - f["size"] += [] (string v) {return v.size ();}; + f["size"] += [] (strings v) {return v.size ();}; + f["size"] += [] (map<string, string> v) {return v.size ();}; + f["size"] += [] (string v) {return v.size ();}; // $sort(<strings> [, <flags>]) // @@ -204,6 +206,21 @@ namespace build2 return find_index (vs, move (v), move (fs)); }; + // $keys(<string-map>) + // + // Return the list of keys in a string map. + // + // Note that the result is sorted in ascending order. + // + f["keys"] += [](map<string, string> v) + { + strings r; + r.reserve (v.size ()); + for (pair<const string, string>& p: v) + r.push_back (p.first); // @@ PERF: use C++17 map::extract() to steal. + return r; + }; + // String-specific overloads from builtins. // function_family b (m, "builtin"); |