Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Make operator* and operator-> const in all iterators. #92

Open
wants to merge 2 commits into
base: master
Choose a base branch
from

Conversation

thomas001
Copy link

C++ iterators basically model pointers. Hence a const pointer can still be dereferenced to a mutable object (T * const not const T*). This is not true for many iterators in itertools since they only have non-const versions of operator*. This also violates C++ iterator concepts, see the github issue.

This change basically replaces all non-const dereference operators with const ones. This was straight forward in most cases:

  • Some iterators own the data they return (note: that probably violates LegacyForwardIterator). So those data fields were changed to mutable.
  • GroupBy advances the group while dereferencing. This does not work when the iterator is constant. Moved the advancing to the constructor and increment operators. This is the only real behavior change, please review carefully.

Fixes #91 .

Thomas Weidner added 2 commits February 25, 2023 13:04
C++ iterators basically model pointers. Hence a const pointer can still
be dereferenced to a mutable object (`T * const` *not* `const T*`). This
is not true for many iterators in itertools since they only have
non-`const` versions of `operator*`. This also violates C++ iterator
concepts, see [the github issue](ryanhaining#91).

This change basically replaces all non-`const` dereference operators
with `const` ones. This was straight forward in most cases:

- Some iterators own the data they return (note: that probably violates
  [`LegacyForwardIterator`](https://en.cppreference.com/w/cpp/named_req/ForwardIterator)).
  So those data fields were changed to `mutable`.
- `GroupBy` advances the group while dereferencing. This does not work
  when the iterator is constant. Moved the advancing to the constructor
  and increment operators. This is the only real behavior change, please
  review carefully.
Just specializing on `T*` misses cv-qualified pointer types like `int
*const`. This change uses `std::is_pointer_v` instead to determine
whether a type is a pointer.
Copy link
Owner

@ryanhaining ryanhaining left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks for working on this

I'm not sure how you formatted but clang-format -i --style=file $filename will match the existing style.

As-written I can't merge this without breaking existing uses because if anyone's sub_iter_ only has a non-const operator* then it breaks. I know that's arguably the fault of the caller, but we can't break them, and those uses do exist.

I believe the combinatoric ones can be changed to return const references rather than holding a mutable member.

groupby is the most complex tool and I will need more time to convince myself everything is okay with this change

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

dereference operators should be const
2 participants