Могу ли я использовать STD :: Views :: Transform для создания абстрактных базовых классов?C++

Программы на C++. Форум разработчиков
Ответить
Anonymous
 Могу ли я использовать STD :: Views :: Transform для создания абстрактных базовых классов?

Сообщение Anonymous »

Следующий код не компилирован.

Код: Выделить всё

#include 
#include 
#include 
#include 

class Base
{
public:
virtual ~Base() = default;
virtual auto say() const -> void = 0;
};

class Derived : public Base
{
public:
auto say() const -> void override
{
std::cout  void
{
for (auto const & base : bases)
{
base.say();
}
}

int main()
{
std::vector bases;
bases.push_back(std::make_unique());
bases.push_back(std::make_unique());

say_all(bases | std::views::transform([](auto const & up) { return static_cast(*(up.get())); }));
}
< /code>
Ошибка под GCC довольно длинная: < /p>
: In instantiation of 'main():: [with auto:11 = std::unique_ptr]':
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/type_traits:3302:30:   required from 'struct std::is_invocable'
3302 |     : public __bool_constant
|                              ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/type_traits:3707:71:   required from 'constexpr const bool std::is_invocable_v'
3707 |   inline constexpr bool is_invocable_v = is_invocable::value;
|                                                                       ^~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/concepts:362:25:   required by substitution of 'template  requires (input_range) && (copy_constructible) && ((view) && (is_object_v) && (regular_invocable) && (__can_reference)) class std::ranges::transform_view [with _Vp = std::ranges::ref_view; _Fp = main()::]'
362 |     concept invocable = is_invocable_v;
|                         ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:2244:5:   required by substitution of 'template std::ranges::transform_view(_Range&&, _Fp) -> transform_view [with _Range = std::vector&; _Fp = main()::]'
2244 |     transform_view(_Range&&, _Fp) -> transform_view;
|     ^~~~~~~~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:933:44:   recursively required by substitution of 'template  requires  __adaptor_invocable constexpr auto std::ranges::views::__adaptor::_Partial::operator()(_Range&&) const [with _Range = std::vector&]'
933 |       = requires { std::declval()(declval()...); };
|                    ~~~~~~~~~~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:933:44:   required by substitution of 'template  requires (__is_range_adaptor_closure) && (__adaptor_invocable) constexpr auto std::ranges::views::__adaptor::operator|(_Range&&, _Self&&) [with _Self = std::ranges::views::__adaptor::_Partial;  _Range = std::vector&]'
:37:107:   required from here
37 |     say_all(bases | std::views::transform([](auto const & up) { return static_cast(*(up.get())); }));
|                                                                                                           ^
:37:72: error: cannot allocate an object of abstract type 'Base'
37 |     say_all(bases | std::views::transform([](auto const & up) { return static_cast(*(up.get())); }));
|                                                                        ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
:7:7: note:   because the following virtual functions are pure within 'Base':
7 | class Base
|       ^~~~
:11:22: note:     'virtual void Base::say() const'
11 |         virtual auto say() const -> void = 0;
|                      ^~~
: In function 'int main()':
:37:19: error: no match for 'operator|' (operand types are 'std::vector' and 'std::ranges::views::__adaptor::_Partial')
37 |     say_all(bases | std::views::transform([](auto const & up) { return static_cast(*(up.get())); }));
|             ~~~~~ ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|             |                            |
|             |                            std::ranges::views::__adaptor::_Partial
|             std::vector
:37:19: note: there are 7 candidates
37 |     say_all(bases | std::views::transform([](auto const & up) { return static_cast(*(up.get())); }));
|             ~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
In file included from :3:
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:981:5: note: candidate 1: 'template  requires (__is_range_adaptor_closure) && (__is_range_adaptor_closure) constexpr auto std::ranges::views::__adaptor::operator|(_Lhs&&, _Rhs&&)'
981 |     operator|(_Lhs&& __lhs, _Rhs&& __rhs)
|     ^~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:981:5: note: template argument deduction/substitution failed:
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:981:5: note: constraints not satisfied
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges: In substitution of 'template  requires (__is_range_adaptor_closure) && (__is_range_adaptor_closure) constexpr auto std::ranges::views::__adaptor::operator|(_Lhs&&, _Rhs&&) [with _Lhs = std::vector&; _Rhs = std::ranges::views::__adaptor::_Partial]':
:37:107:   required from here
37 |     say_all(bases | std::views::transform([](auto const & up) { return static_cast(*(up.get())); }));
|                                                                                                           ^
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:962:13:   required for the satisfaction of '__is_range_adaptor_closure' [with _Lhs = std::vector&]
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:963:9:   in requirements with '_Tp __t' [with _Tp = std::vector&]
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:963:70: note: the required expression 'std::ranges::views::__adaptor::__is_range_adaptor_closure_fn(__t, __t)' is invalid
963 |       = requires (_Tp __t) { __adaptor::__is_range_adaptor_closure_fn(__t, __t);  };
|                              ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^~~~~~~~~~
cc1plus: note: set '-fconcepts-diagnostics-depth=' to at least 2 for more detail
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:972:5: note: candidate 2: 'template  requires (__is_range_adaptor_closure) && (__adaptor_invocable) constexpr auto std::ranges::views::__adaptor::operator|(_Range&&, _Self&&)'
972 |     operator|(_Range&& __r, _Self&& __self)
|     ^~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ranges:972:5: note: substitution of deduced template arguments resulted in errors seen above
In file included from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/memory_resource.h:40,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/string:72,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/locale_classes.h:42,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ios_base.h:43,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ios:46,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ostream.h:43,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/ostream:42,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/iostream:43,
from :1:
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/cstddef:141:3: note: candidate 3: 'constexpr std::byte std::operator|(byte, byte)'
141 |   operator|(byte __l, byte __r) noexcept
|   ^~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/cstddef:141:18: note: no known conversion for argument 1 from 'std::vector' to 'std::byte'
141 |   operator|(byte __l, byte __r) noexcept
|             ~~~~~^~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ios_base.h:91:3: note: candidate 4: 'constexpr std::_Ios_Fmtflags std::operator|(_Ios_Fmtflags, _Ios_Fmtflags)'
91 |   operator|(_Ios_Fmtflags __a, _Ios_Fmtflags __b) _GLIBCXX_NOTHROW
|   ^~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ios_base.h:91:27: note: no known conversion for argument 1 from 'std::vector' to 'std::_Ios_Fmtflags'
91 |   operator|(_Ios_Fmtflags __a, _Ios_Fmtflags __b) _GLIBCXX_NOTHROW
|             ~~~~~~~~~~~~~~^~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ios_base.h:150:3: note: candidate 5: 'constexpr std::_Ios_Openmode std::operator|(_Ios_Openmode, _Ios_Openmode)'
150 |   operator|(_Ios_Openmode __a, _Ios_Openmode __b) _GLIBCXX_NOTHROW
|   ^~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ios_base.h:150:27: note: no known conversion for argument 1 from 'std::vector' to 'std::_Ios_Openmode'
150 |   operator|(_Ios_Openmode __a, _Ios_Openmode __b) _GLIBCXX_NOTHROW
|             ~~~~~~~~~~~~~~^~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ios_base.h:197:3: note: candidate 6: 'constexpr std::_Ios_Iostate std::operator|(_Ios_Iostate, _Ios_Iostate)'
197 |   operator|(_Ios_Iostate __a, _Ios_Iostate __b) _GLIBCXX_NOTHROW
|   ^~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/ios_base.h:197:26: note: no known conversion for argument 1 from 'std::vector' to 'std::_Ios_Iostate'
197 |   operator|(_Ios_Iostate __a, _Ios_Iostate __b) _GLIBCXX_NOTHROW
|             ~~~~~~~~~~~~~^~~
In file included from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/shared_ptr_atomic.h:33,
from /cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/memory:83,
from :2:
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/atomic_base.h:104:3: note: candidate 7: 'constexpr std::memory_order std::operator|(memory_order, __memory_order_modifier)'
104 |   operator|(memory_order __m, __memory_order_modifier __mod) noexcept
|   ^~~~~~~~
/cefs/22/22e6cdc013c8541ce3d1548e_consolidated/compilers_c++_x86_gcc_15.2.0/include/c++/15.2.0/bits/atomic_base.h:104:26: note: no known conversion for argument 1 from 'std::vector' to 'std::memory_order'
104 |   operator|(memory_order __m, __memory_order_modifier __mod) noexcept
|             ~~~~~~~~~~~~~^~~
Compiler returned: 1
По сути, он жалуется, что не может создать объект типа Base , поскольку это абстрактный класс. Но почему он пытается? Код здесь может не иметь большого смысла, но он дистиллирован из более широкого примера, который использует множественное наследование и просто служит целью иллюстрации проблемы.

Подробнее здесь: https://stackoverflow.com/questions/797 ... se-classes
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «C++»