Boost :: anyone violates Liskov's principle of substitution

I found that it is not possible to extract the reference to the base type from boost::any , which contains the derived type:

 boost::any holder = Derived(); const Base& base_ref = boost::any_cast<const Base&>(holder); 

throws a boost::bad_any_cast .

It seems that this is a violation of the principle of replacing Liskov and is not very convenient. Are there any workarounds?

+4
source share
2 answers

I do not think that it "breaks" it - boost::any not intended for the fact that you use it.

It is specially designed to work with type values ​​(see the documents to which you already posted a link).

You must any_cast exactly indicate the type of any variable; under the hood, he checks the type. Clearly, const Base& does not match for Derived in this case.

std::shared_ptr< Base > provides / almost / what you think is needed. Or look here for more information.

+5
source

The principle of substitution is still applied in the sense that the code compiles and works. The boost::any design is such that it throws an exception (and you can restore it if you want).

The alternative boost::any design might do something else. For a thinner version of boost :: any you can look at Boost.TypeErasure. (Although probably std::unique_ptr will do the job you want.)

0
source

Source: https://habr.com/ru/post/1491845/


All Articles