smart pointer kopiowanie

0

Mam problem ze skopiowaniem smart wskaznika do drugiego smart wskaznika razem ze skopiowaniem objektu który zawiera bez uzycia konstruktora.

class test
{
    public:
    test(bool x )
     {
         //....
     }
};
std::unique_ptr<test> a;
a = std::unique_ptr<test>(new test(true));
std::unique_ptr<test> b;
b = a; // nie dziala
// celem jest posiadanie dwóch obiektów typu test.

Nie mogę nigdzie wyczytać jak to zrobić.

1

unique_ptr jak nazwa wskazuje nie jest kopiowalny, użyj std:shared_ptr jak chcesz kopiować

also do inicjalizacji używaj std::make_unique, std::make_shared zamiast new

0

Możesz podać przykład jak to skopiować uzywając shared_ptr? Bo przez operator = wskazują mi oba na ten sam objekt

1

no bo tak to działa, a co chcesz żeby Ci pokazało?

mówisz o kopiowaniu a nie o move'owaniu

2

Jak chcesz skopiować obiekt to musisz skopiować obiekt, a nie wskaźnik.

0

Już to rozwiązałem, ale czy da się to zrobić innym/lepszym sposobem?

class test
{
    public:
        bool bol;
    test(bool x )
    : bol(x)
     {
         //....
     }
};
test x(true);
std::shared_ptr<test> a;
a = std::make_shared<test>(x);
std::shared_ptr<test> b;
b = std::make_shared<test>(*a);
b->bol = false;
std::cout << a->bol << " : " << b->bol; // wynik 1 : 0 - mam dwa objekty. 
0
std::shared_ptr<test> a = std::make_shared<test>(true);
std::shared_ptr<test> b = std::make_shared<test>(false);
std::cout << a->bol << " : " << b->bol; // wynik 1 : 0 - mam dwa objekty.
3

To też zadziała dla std::unique_ptr. Jak nie potrzebujesz wielu kopii tego wskaźnika to używaj unique_ptr.

0

Myślałem ze rozwiązałem ten problem, aczkolwiek pojawił się kolejny. Pomiając poprzednie przykłady:

class baza
{
virtual void abstrakcyjna() =0;

};
class a : public baza
{
void abstrakcyjna() override
{
    // ...
}
};
class b : public baza
{
void abstrakcyjna() override
{
    // ...
}
};
   std::shared_ptr<baza> A;
    std::shared_ptr<baza> B;

    a aa;
    A = std::make_shared<a>(aa);
    // jak to skopiowac, skoro nie wiem (teoretycznie)
    // jaki ma typ tzn. czy a czy b
    B = std::make_shared<???>(*A);
1
#include <iostream>
#include <memory>

struct Base
{
    virtual void print() = 0;  
};

struct A : Base
{
    virtual void print() override final { std::cout << "A\n"; }
};

struct B : Base
{
    virtual void print() override final { std::cout << "B\n"; }
};

int main()
{
    using ptr = std::shared_ptr<Base>;
    ptr b = std::make_shared<B>();
    b->print();
    ptr a = std::make_shared<A>();
    a->print();
    ptr copyB = std::make_shared<B>(*static_cast<B*>(b.get()));
    copyB->print();
    ptr copyA = std::make_shared<A>(*static_cast<A*>(a.get()));
    copyA->print();
    
    return 0;
}

http://melpon.org/wandbox/permlink/gWmoKCwlklyWS5eO

jeszcze jest static_pointer_cast dla std::shared_ptr

edit:

to jest jak znasz typ, a jak nie to idiom clone, o którym wspomniał @kq

1

W takim wypadku musisz mieć abstrakcyjną metodę clone (nazwa dowolna, ale taka jest najczęściej używana) i za jej pomocą tworzyć kopię.

1 użytkowników online, w tym zalogowanych: 0, gości: 1