Most answers relate to the overhead of virtual functions, but there are other reasons not to do any functions in the virtual class, since the fact that it will change the class from a standard layout to, well, a non-standard layout, and this can be a problem if you need to serialize binary data. This is solved differently in C #, for example, if the struct is a different type family than class es.
From a design point of view, each public function sets up a contract between your type and users of the type, and each virtual function (public or not) sets up a different contract with classes that extend your type. The greater the number of such contracts that you sign, the less opportunities for changes that you have. In fact, there are quite a few people, including well-known writers, who advocate that the public interface should never contain virtual functions, since your compromise for your clients may differ from the compromises that you require from your extensions. That is, the public interfaces show what you are doing for your customers, and the virtual interface shows how others can help you with this.
Another effect of virtual functions is that they are always sent to the final override (unless you explicitly qualify the call), which means that any function needed to maintain your invariants (consider the state of private variables) should not be virtual: if the class expands it, he will have to either make an explicit qualified call to the parent, or otherwise violate the invariants at your level.
This is similar to the example of the infinite loop / stack overflow mentioned in @Jon Skeet, in a different way: you should document in each function whether it receives any private attributes so that the extensions ensure that this function is available at the right time. And this, in turn, means that you break encapsulation, and you have an absorbing abstraction: your internal details are now part of the interface (documentation + requirements for your extensions), and you cannot change them at your discretion.
Then there is performance ... there will be an effect on performance, but in most cases it is overrated, and it can be argued that only in the few cases where performance is critical do you back down and declare the functions non-virtual. Again, this can be difficult for the embedded product, as the two interfaces (public + extensions) are already connected.
David Rodríguez - dribeas Jul 07 2018-11-11T00: 00Z
source share