Skip to content

Commit

Permalink
fixup! WIP: [libc++][ranges] Implement ranges::stride_view.
Browse files Browse the repository at this point in the history
Updating tests based on feedback.

Signed-off-by: Will Hawkins <[email protected]>
  • Loading branch information
hawkinsw committed Jun 25, 2024
1 parent 6e310c4 commit f44d250
Show file tree
Hide file tree
Showing 5 changed files with 81 additions and 11 deletions.
6 changes: 3 additions & 3 deletions libcxx/include/__ranges/stride_view.h
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,7 @@ class stride_view : public view_interface<stride_view<_View>> {
return __stride_;
}

_LIBCPP_NODISCARD _LIBCPP_NODISCARD _LIBCPP_HIDE_FROM_ABI constexpr auto begin()
_LIBCPP_NODISCARD _LIBCPP_HIDE_FROM_ABI constexpr auto begin()
requires(!__simple_view<_View>)
{
return __iterator<false>(this, ranges::begin(__base_), 0);
Expand Down Expand Up @@ -391,8 +391,8 @@ namespace __stride {
struct __fn {
template <viewable_range _Range>
[[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr auto operator()(_Range&& __range, range_difference_t<_Range> __n) const
noexcept(noexcept(/**/ stride_view{
std::forward<_Range>(__range), __n})) -> decltype(/*--*/ stride_view{std::forward<_Range>(__range), __n}) {
noexcept(noexcept(/**/ stride_view{std::forward<_Range>(__range), __n}))
-> decltype(/*--*/ stride_view{std::forward<_Range>(__range), __n}) {
return /*-------------*/ stride_view(std::forward<_Range>(__range), __n);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
//===----------------------------------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20

// Test that appropriate (member) functions are properly marked no_discard

#include <ranges>

#include "../../../../std/ranges/range.adaptors/range.stride.view/types.h"

void test() {
const int range[] = {1, 2, 3};

std::views::stride( // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
range, 2);
range | std::views::stride( // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
2);
std::views::all | // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
std::views::stride(
1);

auto sv = std::views::stride(range, 2);
const auto const_sv = std::views::stride(range, 2);
auto unsimple_sv = std::views::stride(UnsimpleConstView{}, 2);

const_sv.base(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
std::move(sv).base(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}

const_sv.stride(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}

const_sv.begin(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
unsimple_sv.begin(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}

const_sv.end(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
unsimple_sv.end(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}

sv.size(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
const_sv.size(); // expected-warning {{ignoring return value of function declared with 'nodiscard' attribute}}
}
Original file line number Diff line number Diff line change
Expand Up @@ -46,11 +46,21 @@ constexpr bool base_const() {

return true;
}

bool base_move() {
auto view = BasicTestView<SizedInputIterator>{SizedInputIterator(), SizedInputIterator()};
auto sv = std::ranges::stride_view<BasicTestView<SizedInputIterator>>(view, 1);
[[maybe_unused]] auto result = sv.begin().base();
assert(result.move_counter==1);
assert(result.copy_counter==0);
return true;
}

int main(int, char**) {
base_noexcept();
static_assert(base_noexcept());
base_const();
static_assert(base_const());

base_move();
return 0;
}
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
#include "../types.h"
#include "__compare/three_way_comparable.h"
#include "__concepts/equality_comparable.h"
#include "__concepts/same_as.h"
#include "__iterator/concepts.h"
#include "__iterator/default_sentinel.h"
#include "__iterator/distance.h"
Expand Down
28 changes: 21 additions & 7 deletions libcxx/test/std/ranges/range.adaptors/range.stride.view/types.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,12 @@
#ifndef TEST_STD_RANGES_RANGE_ADAPTORS_RANGE_STRIDE_TYPES_H
#define TEST_STD_RANGES_RANGE_ADAPTORS_RANGE_STRIDE_TYPES_H

#include <functional>
#include <iterator>
#include <ranges>
#include <type_traits>

#include "__concepts/constructible.h"
#include "__iterator/concepts.h"
#include "__ranges/common_view.h"
#include "test_iterators.h"
Expand All @@ -21,7 +23,7 @@
// Concepts

template <typename Iter>
concept IterDifferable = requires(Iter& t) { t - t; };
concept IterDifferable = std::invocable<std::minus<>,Iter, Iter>;

// Iterators

Expand All @@ -33,15 +35,26 @@ struct InputIterBase {
using value_type = typename std::iterator_traits<Iter>::value_type;
using difference_type = typename std::iterator_traits<Iter>::difference_type;

int copy_counter = 0;
int move_counter = 0;

Iter value_{};

constexpr InputIterBase() = default;
constexpr InputIterBase(const InputIterBase&) = default;
constexpr InputIterBase(InputIterBase&&) = default;
constexpr InputIterBase& operator=(const InputIterBase& other) = default;
constexpr InputIterBase& operator=(InputIterBase&& other) = default;
constexpr InputIterBase() = default;
constexpr explicit InputIterBase(Iter value) : value_(value) {}

constexpr InputIterBase(const InputIterBase& other) noexcept {
copy_counter++;
value_ = other.value_;
}

constexpr InputIterBase(InputIterBase&& other) noexcept {
move_counter++;
value_ = std::move(other.value_);
}
constexpr InputIterBase& operator=(const InputIterBase& other) = default;
constexpr InputIterBase& operator=(InputIterBase&& other) = default;

constexpr value_type operator*() const { return *value_; }
constexpr Derived& operator++() {
value_++;
Expand All @@ -60,7 +73,7 @@ struct InputIterBase {
}
};

struct UnsizedInputIterator : InputIterBase<UnsizedInputIterator> {};
struct UnsizedInputIterator : InputIterBase<UnsizedInputIterator /*, Iter = int *, IsSized = false */> {};
static_assert(std::input_iterator<UnsizedInputIterator>);
static_assert(!std::sized_sentinel_for<UnsizedInputIterator, UnsizedInputIterator>);

Expand Down Expand Up @@ -249,6 +262,7 @@ using UnSimpleNoConstCommonView = MaybeConstCommonSimpleView<false, false, true>
using UnsimpleConstView = MaybeConstCommonSimpleView<false, true, true>;
using UnsimpleUnCommonConstView = MaybeConstCommonSimpleView<false, true, false>;
using SimpleUnCommonConstView = MaybeConstCommonSimpleView<true, true, false>;
using SimpleCommonConstView = MaybeConstCommonSimpleView<true, true, true>;

// Ranges

Expand Down

0 comments on commit f44d250

Please sign in to comment.