ошибка оператора присваивания в уникальном указателе - PullRequest
0 голосов
/ 27 января 2019

Я пытался использовать unique_ptr в c ++ в шаблоне синглтона вместо необработанного указателя.когда я хочу присвоить unique_ptr другому, я получил ошибку.Я пытался использовать std::move для назначения, но это не сработало.код выглядит следующим образом:

#include <iostream>
#include <memory>
#include <list>
#include <algorithm>
#include <iterator>
#include <string>

using namespace std;

class ClientDB
{
  private:
    static unique_ptr<ClientDB> theDB;
    ClientDB() {}
    list<string> clients;
  public:
    ~ClientDB() {}
    static unique_ptr<ClientDB> getInstance()
    {
      if(theDB==nullptr)
    theDB = make_unique<ClientDB>;
      return theDB;
    }
    void addClient(string c) {clients.push_back(c);}
    void printClients(ostream& os)
    {
      copy(clients.cbegin(),clients.cend(),ostream_iterator<string>{os,"\n"});
    }
};


int main()
{
  unique_ptr<ClientDB> db1{ClientDB::getInstance()};
  db1->addClient("Mr. Schultz");
  unique_ptr<ClientDB> db2{ClientDB::getInstance()};
  db2->addClient("Mrs. James");
  unique_ptr<ClientDB> db3{ClientDB::getInstance()};
  db3->addClient("Mr. Karajan");
  db1->printClients(cout);
}

, и я получил ошибку

error: no match for ‘operator=’ (operand types are ‘std::unique_ptr<ClientDB>’ and ‘<unresolved overloaded function type>’)
     theDB = make_unique<ClientDB>;

, и другой вопрос, может ли nullptr использоваться для unique_ptr.

1 Ответ

0 голосов
/ 01 февраля 2019

Наконец, с помощью моего учителя я могу решить эту проблему. Есть некоторые моменты, которые следует учитывать.

1 - для назначения unique_ptr, следует использовать std::move::.

2- make_unique не имеет доступа к приватному конструктору, конструктор должен вызываться явно: theDB = unique_ptr<ClientDB>(new ClientDB());

3-* unique-ptr должен быть инициализирован вне класса: unique_ptr<ClientDB> ClientDB::theDB;

4 - Три уникальных указателя в основном для одного и того же объекта не могут быть использованы, только один допускается для уникальности. ссылки на unique_ptr должны использоваться вместо: unique_ptr<ClientDB>& db1=ClientDB::getInstance();

и, наконец, код должен быть таким:

#include <iostream>
#include <memory>
#include <list>
#include <algorithm>
#include <iterator>
#include <string>

using namespace std;

class ClientDB
{
private:
  static unique_ptr<ClientDB> theDB;
  ClientDB() {}
  list<string> clients;
public:
  ~ClientDB() {}
  static unique_ptr<ClientDB>& getInstance()
  {
    if(theDB==nullptr)
      //theDB = move(make_unique<ClientDB>());
      theDB = unique_ptr<ClientDB>(new ClientDB());
    return theDB;
  }
  void addClient(string c) {clients.push_back(c);}
  void printClients(ostream& os)
  {
    copy(clients.cbegin(),clients.cend(),ostream_iterator<string>{os,"\n"});
  }
};
unique_ptr<ClientDB> ClientDB::theDB;

int main()
{
  unique_ptr<ClientDB>& db1=ClientDB::getInstance();
  db1->addClient("Mr. Schultz");


  unique_ptr<ClientDB>& db2=ClientDB::getInstance();
  db2->addClient("Mrs. James");


  unique_ptr<ClientDB>& db3=ClientDB::getInstance();
  db3->addClient("Mr. Karajan");

  db1->printClients(cout);
}
...