Невозможно использовать карту если я не определю конструктор по умолчанию без аргументов для Custom_Class - PullRequest
0 голосов
/ 10 апреля 2020
#include<bits/stdc++.h>
using namespace std;

class Cat
{
    public:
        string name;
        // Cat(){}
        Cat(string name_given)
        {
            this->name=name_given;
        }
};

class House
{
    public: 
        vector<Cat> Cats;
        map<string,Cat> CatName_Cat;
        House(string CatName)
        {
            generateHouse(CatName);
        }

    private:
        void generateHouse(string cName)
        {
            Cat p(cName);
            this->Cats.push_back(p);
            this->CatName_Cat[p.name]=p;
        }
};
int main()
{
    Cat p("McCat");
}

Приведенный выше код не работает, если я не выполню одно из двух следующих действий: -

(1) Удалите использование карты.

(2) Определите пустое Конструктор, который не запрашивает аргументы.

Используется ли пустой Конструктор? Я пытался делать cout<<"used\n"; каждый раз, когда он вызывался, и вывод был пустым.

Ошибка: -

In file included from /usr/include/c++/7/functional:54:0,
                 from /usr/include/x86_64-linux-gnu/c++/7/bits/stdc++.h:71,
                 from dumber.cpp:1:
/usr/include/c++/7/tuple: In instantiation of ‘std::pair<_T1, _T2>::pair(std::tuple<_Args1 ...>&, std::tuple<_Args2 ...>&, std::_Index_tuple<_Indexes1 ...>, std::_Index_tuple<_Indexes2 ...>) [with _Args1 = {const std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >&}; long unsigned int ..._Indexes1 = {0}; _Args2 = {}; long unsigned int ..._Indexes2 = {}; _T1 = const std::__cxx11::basic_string<char>; _T2 = Cat]’:
/usr/include/c++/7/tuple:1641:63:   required from ‘std::pair<_T1, _T2>::pair(std::piecewise_construct_t, std::tuple<_Args1 ...>, std::tuple<_Args2 ...>) [with _Args1 = {const std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >&}; _Args2 = {}; _T1 = const std::__cxx11::basic_string<char>; _T2 = Cat]’
/usr/include/c++/7/ext/new_allocator.h:136:4:   required from ‘void __gnu_cxx::new_allocator<_Tp>::construct(_Up*, _Args&& ...) [with _Up = std::pair<const std::__cxx11::basic_string<char>, Cat>; _Args = {const std::piecewise_construct_t&, std::tuple<const std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >&>, std::tuple<>}; _Tp = std::_Rb_tree_node<std::pair<const std::__cxx11::basic_string<char>, Cat> >]’
/usr/include/c++/7/bits/alloc_traits.h:475:4:   required from ‘static void std::allocator_traits<std::allocator<_CharT> >::construct(std::allocator_traits<std::allocator<_CharT> >::allocator_type&, _Up*, _Args&& ...) [with _Up = std::pair<const std::__cxx11::basic_string<char>, Cat>; _Args = {const std::piecewise_construct_t&, std::tuple<const std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >&>, std::tuple<>}; _Tp = std::_Rb_tree_node<std::pair<const std::__cxx11::basic_string<char>, Cat> >; std::allocator_traits<std::allocator<_CharT> >::allocator_type = std::allocator<std::_Rb_tree_node<std::pair<const std::__cxx11::basic_string<char>, Cat> > >]’
/usr/include/c++/7/bits/stl_tree.h:626:32:   required from ‘void std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::_M_construct_node(std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::_Link_type, _Args&& ...) [with _Args = {const std::piecewise_construct_t&, std::tuple<const std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >&>, std::tuple<>}; _Key = std::__cxx11::basic_string<char>; _Val = std::pair<const std::__cxx11::basic_string<char>, Cat>; _KeyOfValue = std::_Select1st<std::pair<const std::__cxx11::basic_string<char>, Cat> >; _Compare = std::less<std::__cxx11::basic_string<char> >; _Alloc = std::allocator<std::pair<const std::__cxx11::basic_string<char>, Cat> >; std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::_Link_type = std::_Rb_tree_node<std::pair<const std::__cxx11::basic_string<char>, Cat> >*]’
/usr/include/c++/7/bits/stl_tree.h:643:21:   required from ‘std::_Rb_tree_node<_Val>* std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::_M_create_node(_Args&& ...) [with _Args = {const std::piecewise_construct_t&, std::tuple<const std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >&>, std::tuple<>}; _Key = std::__cxx11::basic_string<char>; _Val = std::pair<const std::__cxx11::basic_string<char>, Cat>; _KeyOfValue = std::_Select1st<std::pair<const std::__cxx11::basic_string<char>, Cat> >; _Compare = std::less<std::__cxx11::basic_string<char> >; _Alloc = std::allocator<std::pair<const std::__cxx11::basic_string<char>, Cat> >; std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::_Link_type = std::_Rb_tree_node<std::pair<const std::__cxx11::basic_string<char>, Cat> >*]’
/usr/include/c++/7/bits/stl_tree.h:2398:33:   required from ‘std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::iterator std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::_M_emplace_hint_unique(std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::const_iterator, _Args&& ...) [with _Args = {const std::piecewise_construct_t&, std::tuple<const std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >&>, std::tuple<>}; _Key = std::__cxx11::basic_string<char>; _Val = std::pair<const std::__cxx11::basic_string<char>, Cat>; _KeyOfValue = std::_Select1st<std::pair<const std::__cxx11::basic_string<char>, Cat> >; _Compare = std::less<std::__cxx11::basic_string<char> >; _Alloc = std::allocator<std::pair<const std::__cxx11::basic_string<char>, Cat> >; std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::iterator = std::_Rb_tree_iterator<std::pair<const std::__cxx11::basic_string<char>, Cat> >; std::_Rb_tree<_Key, _Val, _KeyOfValue, _Compare, _Alloc>::const_iterator = std::_Rb_tree_const_iterator<std::pair<const std::__cxx11::basic_string<char>, Cat> >]’
/usr/include/c++/7/bits/stl_map.h:493:8:   required from ‘std::map<_Key, _Tp, _Compare, _Alloc>::mapped_type& std::map<_Key, _Tp, _Compare, _Alloc>::operator[](const key_type&) [with _Key = std::__cxx11::basic_string<char>; _Tp = Cat; _Compare = std::less<std::__cxx11::basic_string<char> >; _Alloc = std::allocator<std::pair<const std::__cxx11::basic_string<char>, Cat> >; std::map<_Key, _Tp, _Compare, _Alloc>::mapped_type = Cat; std::map<_Key, _Tp, _Compare, _Alloc>::key_type = std::__cxx11::basic_string<char>]’
dumber.cpp:30:28:   required from here
/usr/include/c++/7/tuple:1652:70: error: no matching function for call to ‘Cat::Cat()’
         second(std::forward<_Args2>(std::get<_Indexes2>(__tuple2))...)
                                                                      ^
dumber.cpp:9:3: note: candidate: Cat::Cat(std::__cxx11::string)
   Cat(string name_given)
   ^~~
dumber.cpp:9:3: note:   candidate expects 1 argument, 0 provided
dumber.cpp:4:7: note: candidate: Cat::Cat(const Cat&)
 class Cat
       ^~~
dumber.cpp:4:7: note:   candidate expects 1 argument, 0 provided
dumber.cpp:4:7: note: candidate: Cat::Cat(Cat&&)
dumber.cpp:4:7: note:   candidate expects 1 argument, 0 provided

Я понял, что какая-то часть в реализации карты терпит неудачу, а что и почему?

Ответы [ 2 ]

4 голосов
/ 10 апреля 2020

std::map::operator[] default создает значение, если значение отсутствует на карте, поэтому оно не работает.

Использование std::map::try_emplace или std::map::insert_or_assign вместо:

        void generateHouse(string cName)
        {
            Cat p(cName);
            this->Cats.push_back(p);
            this->CatName_Cat.insert_or_assign(p.name, p);
        }
2 голосов
/ 10 апреля 2020
Оператор

std::map в квадратных скобках default-конструирует элемент, если он еще не существует, как объяснено здесь . Поэтому, если вы вызываете этот оператор, ваш отображаемый тип должен быть конструируемым по умолчанию.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...