[all-commits] [llvm/llvm-project] bf738d: [ADT] Make mapped_iterator copy assignable
kazutakahirata via All-commits
all-commits at lists.llvm.org
Sun Oct 30 14:37:21 PDT 2022
Branch: refs/heads/main
Home: https://github.com/llvm/llvm-project
Commit: bf738d2e77846826964402f2cccdd0681c71c038
https://github.com/llvm/llvm-project/commit/bf738d2e77846826964402f2cccdd0681c71c038
Author: James Player <james.w.player at gmail.com>
Date: 2022-10-30 (Sun, 30 Oct 2022)
Changed paths:
M llvm/include/llvm/ADT/STLExtras.h
M llvm/unittests/ADT/MappedIteratorTest.cpp
Log Message:
-----------
[ADT] Make mapped_iterator copy assignable
As mentioned in https://discourse.llvm.org/t/rfc-extend-ranges-infrastructure-to-better-match-c-20/65377
Lambda objects are not copy assignable, and therefore neither are
iterator types which hold a lambda. STL code require iterators be
copy assignable. Users may not use mapped_iterator with a std::deque
for example: https://godbolt.org/z/4Px7odEEd
This blog post [1] explains the problem and solution. We define a
wrapper class to store callable objects with two specialization.
1. Specialization for non-function types
- Use a std::optional as storage for non-function callable.
- Define operator=() implementation(s) which use
std::optional::emplace() instead of the assignment operator.
2. Specialization for function types
- Store as a pointer (even if template argument is a function reference).
- Default construct pointer to nullptr.
This Callable wrapper class is now default constructible (with invalid
state) and copy/move assignable.
With these new properties available on the callable object,
mapped_iterator can define a default constructor as well.
[1] https://www.fluentcpp.com/2019/04/16/an-alternative-design-to-iterators-and-ranges-using-stdoptional/
Reviewed By: kazu
Differential Revision: https://reviews.llvm.org/D134675
More information about the All-commits
mailing list