1

In a non-const member function, I want to pass 'this' to a function, but the function takes a shared_ptr. When I try to pass it like this:

std::shared_ptr<Piece>(this)

I get weird exceptions saying: "Chess.exe has triggered a breakpoint"

Am I converting from 'this' to shared_ptr in the wrong way?

JensB
  • 839
  • 4
  • 19
  • 1
    [like that](https://en.cppreference.com/w/cpp/memory/enable_shared_from_this) – pptaszni Nov 16 '20 at 17:03
  • 1
    @pptaszni This would work only if `*this` is already managed by a shared pointer. – Daniel Langr Nov 16 '20 at 17:04
  • @Daniel Langr So how should I do this instead? – JensB Nov 16 '20 at 17:05
  • Yup, that's true, it needs to be managed by `shared_ptr` already. If it is not, can you show the full example of what you are trying to do. Maybe there is some design issue. – pptaszni Nov 16 '20 at 17:09
  • please include a [mcve] in the question – 463035818_is_not_an_ai Nov 16 '20 at 17:09
  • You can create a "non-owning" shared pointer with no-op deleter: `std::shared_ptr(this, [](Piece*){});`. But I am not sure whether this is legal (definitely this does not correspond with how shared pointers are intended to be used). – Daniel Langr Nov 16 '20 at 17:11
  • Useful reading: [What is the usefulness of `enable_shared_from_this`?](https://stackoverflow.com/questions/712279/what-is-the-usefulness-of-enable-shared-from-this) – user4581301 Nov 16 '20 at 17:47

2 Answers2

1

If you are already using shared pointers to manage the object's memory then this is what std::enable_shared_from_this<T> is for e.g.

#include <memory>

class Piece;

void takes_a_shared_piece(std::shared_ptr<Piece> ptr) {
    //do something
}

class Piece : public std::enable_shared_from_this<Piece> {
public:
    Piece(); 

    void do_something() {
        takes_a_shared_piece( shared_from_this() );
    }
};
jwezorek
  • 8,592
  • 1
  • 29
  • 46
0

Though the above discussions revolve around using the std::enable_shared_from_this, you could do it the original way (C++11 style)by making shared_ptr work in tandem with make_shared. What your code needs is a call like std::make_shared<Piece>(*this) which invokes a non-const member function int foo(std::shared_ptr<T>);. Refer the code below:

#include <memory>

template<typename T>
struct S {
    int foo(std::shared_ptr<T>);
};

class Piece {
    S<Piece> *s;
public:
    Piece () {
        s = new S<Piece>();
    }

    void call_S () {
        s->foo(std::make_shared<Piece>(*this));
    }
};

int main() {
    Piece *knight = new Piece();
    return 0;
}

Remember, you create a shared_ptr by make_shared. Refer to the overloads here: https://en.cppreference.com/w/cpp/memory/shared_ptr/make_shared

Jerry Ajay
  • 1,084
  • 11
  • 26