Skip to content

Commit a497243

Browse files
Fix xt::drop with variables (#2912)
# Checklist - [x] The title and commit message(s) are descriptive. - [x] Small commits made to fix your PR have been squashed to avoid history pollution. - [x] Tests have been added for new features or bug fixes. - [x] API of new functions and classes are documented. # Description Address #2867 Changed `xtl::is_integral<T>::value` to `xtl::is_integral<std::decay_t<T>>::value` in the `drop()` function template. When passing a variable like `size_t index = 1`, `T` deduces to `unsigned long&`, a reference type, which `is_integral` rejects. Decaying strips the reference so the integral branch is correctly taken. --------- Co-authored-by: Alexis Placet <2400067+Alex-PLACET@users.noreply.github.com> Co-authored-by: Johan Mabille <johan.mabille@gmail.com>
1 parent 961722d commit a497243

3 files changed

Lines changed: 43 additions & 1 deletion

File tree

include/xtensor/views/xslice.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -484,7 +484,7 @@ namespace xt
484484
template <class R = std::ptrdiff_t, class T>
485485
inline auto drop(T&& indices)
486486
{
487-
if constexpr (xtl::is_integral<T>::value)
487+
if constexpr (xtl::is_integral<std::remove_cvref_t<T>>::value)
488488
{
489489
using slice_type = xdrop_slice<R>;
490490
using container_type = typename slice_type::container_type;

test/test_xoperation.cpp

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -858,6 +858,29 @@ namespace xt
858858
EXPECT_EQ(expected1, res3);
859859
EXPECT_EQ(expected2, res4);
860860
}
861+
862+
TEST_CASE("divide_4d")
863+
{
864+
using T4 = xt::xtensor<float, 4, xt::layout_type::row_major>;
865+
using shape_type = typename T4::shape_type;
866+
867+
shape_type shape = {2, 3, 2, 2};
868+
T4 a(shape, 4.5f);
869+
T4 b(shape, 1.3f);
870+
871+
EXPECT_EQ((a / b)(0, 0, 0, 0), a(0, 0, 0, 0) / b(0, 0, 0, 0));
872+
873+
float sb = 1.2f;
874+
EXPECT_EQ((a / sb)(0, 0, 0, 0), a(0, 0, 0, 0) / sb);
875+
876+
float sa = 4.6f;
877+
EXPECT_EQ((sa / b)(0, 0, 0, 0), sa / b(0, 0, 0, 0));
878+
879+
// self-divide assignment: a = a / b (no zeros in b)
880+
auto a_before = a(1, 2, 1, 1);
881+
a = a / b;
882+
EXPECT_EQ(a(1, 2, 1, 1), a_before / b(1, 2, 1, 1));
883+
}
861884
}
862885

863886
#undef XOPERATION_TEST_TYPES

test/test_xview.cpp

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1861,4 +1861,23 @@ namespace xt
18611861

18621862
XT_ASSERT_THROW(const auto col = xt::col(arr, 0), std::invalid_argument);
18631863
}
1864+
1865+
TEST(xview, drop_on_1dim_array)
1866+
{
1867+
auto my_array = xt::xtensor<double, 1>({1, 2, 3});
1868+
1869+
// drop(1) creates a view excluding index 1
1870+
auto v1 = xt::view(my_array, xt::drop(1));
1871+
EXPECT_EQ(v1, (xt::xtensor<double, 1>{1, 3}));
1872+
1873+
// Assign through the drop view
1874+
xt::view(my_array, xt::drop(1)) = 0.;
1875+
EXPECT_EQ(my_array, (xt::xtensor<double, 1>{0, 2, 0}));
1876+
1877+
// Reset, then test drop with a variable (the original compilation issue)
1878+
my_array = xt::xtensor<double, 1>({1, 2, 3});
1879+
const size_t index = 1;
1880+
auto v2 = xt::view(my_array, xt::drop(index));
1881+
EXPECT_EQ(v2, (xt::xtensor<double, 1>{1, 3}));
1882+
}
18641883
}

0 commit comments

Comments
 (0)