CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Page 1 of 2 12 LastLast
Results 1 to 15 of 16
  1. #1
    Join Date
    Apr 2009
    Posts
    1,355

    C++: can i create Polymorphism without 'virtual'?

    i'm doing some test code using macros.
    these macro type is only for avoid repeat some lines code.
    on base class, we have a virtual function.
    if on derived class we have a prototype function, we must define it.
    i need try to see if:
    1 - can prototype function without define it;
    2 - or if i can create another another way for Polymorphism.
    what you can advice me?

  2. #2
    VictorN's Avatar
    VictorN is offline Super Moderator Power Poster
    Join Date
    Jan 2003
    Location
    Hanover Germany
    Posts
    20,398

    Re: C++: can i create Polymorphism without 'virtual'?

    Victor Nijegorodov

  3. #3
    Join Date
    Feb 2017
    Posts
    677

    Re: C++: can i create Polymorphism without 'virtual'?

    A base class virtual function that is implemented need not be overridden in a derived class. It's only if the function is pure virtual it must to be overridden. Example,

    Code:
    class Base {
    
        virtual int fun1() =0; // pure virtual - must be overridden (if called)
    
        virtual int fun2() { // virtual and implemented here - need not be overridden
            return 0; 
        }
    
        virtual int fun3(); // virtual and implemented elsewhere - need not be overridden
    
    };
    In C++ there's so called "static polymorphism". It's a way to implement (subtype) polymorphism without use of the virtual keyword. It may be an alternative for you.
    Last edited by wolle; April 26th, 2018 at 05:01 AM.

  4. #4
    Join Date
    Apr 2009
    Posts
    1,355

    Re: C++: can i create Polymorphism without 'virtual'?

    VictorN : i did try even with pure virtual function, but without success
    wolle : i'm sorry, but "static polymorphism" don't means be the same for all instances?
    what i'm trying to do is functions polymorphism, but change for what i need, but don't prototype them or prototype them and just define some.
    (i was getting error for Post.. i'm sorry... so i did the question on Feedback forum.. the problem was coping the name with link?)
    Last edited by Cambalinho; April 26th, 2018 at 02:10 PM.

  5. #5
    2kaud's Avatar
    2kaud is offline Super Moderator Power Poster
    Join Date
    Dec 2012
    Location
    England
    Posts
    7,825

    Re: C++: can i create Polymorphism without 'virtual'?

    Re static polymorphism. Have you read up about the 'Curiously recurring template pattern'? See https://en.wikipedia.org/wiki/Curiou...mplate_pattern

    Re your post #1, you can certainly prototype (declare) a class function without providing a definition. Just don't try calling it!

    I'm not following exactly what you're trying to do?
    All advice is offered in good faith only. All my code is tested (unless stated explicitly otherwise) with the latest version of Microsoft Visual Studio (using the supported features of the latest standard) and is offered as examples only - not as production quality. I cannot offer advice regarding any other c/c++ compiler/IDE or incompatibilities with VS. You are ultimately responsible for the effects of your programs and the integrity of the machines they run on. Anything I post, code snippets, advice, etc is licensed as Public Domain https://creativecommons.org/publicdomain/zero/1.0/ and can be used without reference or acknowledgement. Also note that I only provide advice and guidance via the forums - and not via private messages!

    C++23 Compiler: Microsoft VS2022 (17.6.5)

  6. #6
    Join Date
    Apr 2009
    Posts
    1,355

    Re: C++: can i create Polymorphism without 'virtual'?

    heres the macro that i use for create a class that don't need instances:
    Code:
    #define ClassWithEvents(DerivedClass, MacroEventsUsed, InstanceName, ...) \
                    class InstanceName : public DerivedClass {public: InstanceName():DerivedClass(__VA_ARGS__){;} ~InstanceName(){;}  MacroEventsUsed}InstanceName;
    (the __VA_ARGS__ is for constructor parameters)
    now heres the base class:
    Code:
    class test
    {
        public:
            test()
            {
                   Move();
                   Click();
             }
            virtual Move()=0;
            virtual Click()=0;
    heres another macro for the 'MacroEventsUsed':

    Code:
    #define FormEvents public: void Move(); void Click();
    wheres the a new class using the ClassWithEvents macro:
    Code:
    ClassWithEvents(test,FormEvents, b);
    now i will define the Move():
    Code:
    void b::Move(){ cout << "hello world";}
    like you see i didn't define the Click() function, so i will get 2 errors.
    i can create several class's using the FormEvents macro ID. but instead create several macros, why not 1 macro with all functions?
    is what i'm trying to do.
    (i'm much more close to my big objective... and if you remember some threads that i did, you, more or less, understand what i mean)

  7. #7
    Join Date
    Feb 2017
    Posts
    677

    Re: C++: can i create Polymorphism without 'virtual'?

    Quote Originally Posted by Cambalinho View Post
    like you see i didn't define the Click() function, so i will get 2 errors.
    As I explained, that won't happen if you do this instead:

    Code:
    class test
    {
        public:
            test()
            {
                   Move();
                   Click();
             }
            virtual void Move() {}; // the virtual functions now have default implementations
            virtual void Click() {}; // meaning they can be overridden but must not be overridden
    If you cannot do this to avoid your problem please explain why not?
    Last edited by wolle; April 27th, 2018 at 03:41 AM.

  8. #8
    Join Date
    Apr 2009
    Posts
    1,355

    Re: C++: can i create Polymorphism without 'virtual'?

    the problem is here:
    if i add the function prototype, on derived class, i must define it or i will get these 2 errors:
    1 - "undefined reference to `b::Click'"(continue with same sample);
    2 - "ld returned 1 exit status".

  9. #9
    Join Date
    Feb 2017
    Posts
    677

    Re: C++: can i create Polymorphism without 'virtual'?

    Quote Originally Posted by Cambalinho View Post
    the problem is here:
    if i add the function prototype, on derived class, i must define it or i will get these 2 errors:
    1 - "undefined reference to `b::Click'"(continue with same sample);
    2 - "ld returned 1 exit status".
    And you get this error when using the test base class modified the way I suggested?

    In that case you shouldn't have to override Move nor Click in a subclass. It must be something else that's wrong. Maybe you're not using public inheritance or something? It's hard to know without seeing the code. If you post a minimal complete test case that shows the bug I'm sure someone will be able to help you finding out what's wrong.
    Last edited by wolle; April 27th, 2018 at 08:12 AM.

  10. #10
    Join Date
    Apr 2009
    Posts
    1,355

    Re: C++: can i create Polymorphism without 'virtual'?

    ok... see the entire sample:
    Code:
    #include <iostream>
    
    
    #define ClassWithEvents(DerivedClass, MacroEventsUsed, InstanceName, ...) \
                    class InstanceName : public DerivedClass {public: InstanceName():DerivedClass(__VA_ARGS__){;} \
                    ~InstanceName(){;}  MacroEventsUsed}InstanceName;
    
    
    #define FormEvents public: void MouseClick(); void Move();
    class test
    {
        public:
        test()
        {
            MouseClick();
            Move();
        }
        virtual void MouseClick(){};
        virtual void Move(){};
    };
    
    
    ClassWithEvents(test,FormEvents, b);
    
    
    void b::MouseClick()
    {
        std::cout << "Mouse click";
    }
    /*void b::Move()
    {
       std::cout << "Move";
    }*/
    
    
    int main()
    {
        return 0;
    }
    like you see the Move() have a prototype but not defined(it's a multi-line comment).
    heres the 2 errors:
    1 - "obj\Debug\testingevents.o:testingevents.cpp.rdata$_ZTV1b[__ZTV1b]+0xc)||undefined reference to `b::Move()'|"
    2- "||error: ld returned 1 exit status|"

  11. #11
    Join Date
    Feb 2017
    Posts
    677

    Re: C++: can i create Polymorphism without 'virtual'?

    Quote Originally Posted by Cambalinho View Post
    ok... see the entire sample:
    I've expanded you macros manually and made minimal corrections (marked error 1 and possible error 2) to make the code compile,

    Code:
    //#define ClassWithEvents(DerivedClass, MacroEventsUsed, InstanceName, ...) \
    //                class InstanceName : public DerivedClass {public: InstanceName():DerivedClass(__VA_ARGS__){;} \
    //                ~InstanceName(){;}  MacroEventsUsed}InstanceName;
    
    
    //#define FormEvents public: void MouseClick(); void Move();
    
    class test
    {
        public:
        test()
        {
            MouseClick();
            Move();
        }
        virtual void MouseClick(){};
        virtual void Move(){};
    };
    
    
    //ClassWithEvents(test,FormEvents, b);
    
    class InstanceName : public test { // manual expansion of ClassWithEvents
    public: 
    	InstanceName() : test(/*__VA_ARGS__*/){;} 
    
    	~InstanceName(){;}  
    
    public: 
    	void MouseClick(); 
    //	void Move();                       // error 1
    } b;
    
    
    // void b::MouseClick()                    // possible error 2
    void InstanceName::MouseClick()
    {
        std::cout << "Mouse click";
    }
    /*void b::Move()
    {
       std::cout << "Move";
    }*/
    
    int main()
    {
        return 0;
    }
    Error 1 is that you override the Move function but then never supply an implementation.

    Possible error 2 is that when you supply an implementation for a member function it should be prefixed with the name of the class (InstanceName) and not with the name of an instance (b). (I'm not 100% sure about this but I would use the class name).

    I suggest you re-design this concrete example in small steps until it works the way you want and then define the macros afterwards.

    But one simple possibility in your current design is to use the FormEvents macro to specify the functions you're planning to actually supply an implementation for. If you do this,

    #define FormEvents public: void MouseClick();

    in the sample you provided then it compiles.
    Last edited by wolle; April 28th, 2018 at 04:05 AM.

  12. #12
    Join Date
    Apr 2009
    Posts
    1,355

    Re: C++: can i create Polymorphism without 'virtual'?

    "But one simple possibility in your current design is to use the FormEvents macro to specify the functions you're planning to actually supply an implementation for. If you do this,

    #define FormEvents public: void MouseClick();

    in the sample you provided then it compiles."
    i get your point. but my point is creating a global macro and just define what i need.
    but let me ask you something that you have seen and said: if the problem is the 'virtual' C++ rules... and if i take of the 'virtual', the code compiles, but will always call the base function... is there a way for call the derived function(if is defined)?

  13. #13
    Join Date
    Apr 2009
    Posts
    1,355

    Re: C++: can i create Polymorphism without 'virtual'?

    wolle: see my new test:
    Code:
    class test{
        public:
        template<typename ClassDerived>//getting the derived pointer
        test(ClassDerived *clsPointer)
        {
            try
            {
                clsPointer->MouseClick();
            }
            catch (...)
            {
               MouseClick();
            }
    
    
            try
            {
                clsPointer->Move();
            }
            catch (...)
            {
               Move();
            }
    
    
        }
        void MouseClick(){};
        void Move(){};
    };
    i'm trying testing the errors, but i can't use these way.
    so i need ask you: how can i test if the function is defined?

  14. #14
    Join Date
    Feb 2017
    Posts
    677

    Re: C++: can i create Polymorphism without 'virtual'?

    Quote Originally Posted by Cambalinho View Post
    "
    i get your point. but my point is creating a global macro and just define what i need.
    Well, once you've declared the MouseClic and Move functions in InstanceNames they exist and the compiler will force you to provide implementations for them.

    The only way out of this is to not declare the functions you don't intend to implement!

    So the approach to first introduce a function by declaring it and then try to make it disappear again by withholding the implementation is a dead-end regardless of how ingeniously you try to make it work. At least it seems so to me. On the other hand I know there is a C++ principle called SFINAE. It means that erroneous constructs may be ignored by the compiler. It may apply here somehow but it's beyond me so I have to give up now. Good luck with your endeavour.

    By the way in this code,

    Code:
    class test
    {
        public:
        test()
        {
            MouseClick();
            Move();
        }
        virtual void MouseClick(){};
        virtual void Move(){};
    };
    you should know that the MouseClick and Move functions defined in test will always be called even if those functions happen to be overridden in a derived class. It's because they're called from a constructor of test. During object construction inheritance doesn't work.
    Last edited by wolle; April 28th, 2018 at 11:49 PM.

  15. #15
    Join Date
    Feb 2017
    Posts
    677

    Re: C++: can i create Polymorphism without 'virtual'?

    Quote Originally Posted by Cambalinho View Post
    wolle: see my new test:
    Code:
    class test{
        public:
        template<typename ClassDerived>//getting the derived pointer
        test(ClassDerived *clsPointer)
        {
            try
            {
                clsPointer->MouseClick();
            }
            catch (...)
            {
               MouseClick();
            }
    
    
            try
            {
                clsPointer->Move();
            }
            catch (...)
            {
               Move();
            }
    
    
        }
        void MouseClick(){};
        void Move(){};
    };
    i'm trying testing the errors, but i can't use these way.
    so i need ask you: how can i test if the function is defined?
    Okay so you pass in a ClassDerived object and you want to detect which of the MouseClick and Move functions are defined. If a function is defined in ClassDerived you want it to be called otherwise a default implementation of the function is to be called? Using ordinary inheritance you can do it like this,

    Code:
    class ClassDerivedNull { // Move has a default implementation here
    public:
    	virtual void MouseClick() {std::cout << "MouseClick NULL implementation" << std::endl;};
    	virtual void Move() {std::cout << "Move NULL implementation" << std::endl;};
    };
    
    class ClassDerived : public ClassDerivedNull { // Move is not implemented here but inherited
    public:
    	void MouseClick() override {std::cout << "MouseClick REAL implementation" << std::endl;}
    //    void Move() override {std::cout << "Move REAL implementation" << std::endl;}
    };
    
    class Test {
    public:
    	Test(ClassDerived *clsPointer) {
    		clsPointer->MouseClick(); // calls MouseClick of ClassDerived if defined there, otherwise a "null" version
    		clsPointer->Move();         // calls Move of ClassDerived if defined there, otherwise a "null" version  
    	}
    };
    
    void testing() {
    	ClassDerived d;
    	Test t(&d);
    }
    As I see it, if you declare a function you must implement it. There's no way around it. Inventing new fancy ways to avoid it, and I'm pretty sure this goes also for SFNIAE based approaches, will only move around the compiler error to different places. But if you want to keep trying here's a SFINAE based solution to detecting the existence of a class function at compiletime,

    https://en.wikibooks.org/wiki/More_C...ember_Detector
    Last edited by wolle; April 29th, 2018 at 04:37 AM.

Page 1 of 2 12 LastLast

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured