|
Prev: How can I simulate the operation of mouse Click?
Next: Performance issue: Writing multiple files vs single file using fopen/fwrite
From: nomad on 13 May 2008 05:51 Anyone have any idea why the code below fails to compile? I get the following message when I try: error C2660: 'B::F' : function does not take 2 arguments.' Clearly, B should inherit int F(int, int) from A, the function declaration is not ambiguous in any way, so it seems to me that I should be able to call it, yet the compiler refuses to allow me to do it. If I explicitly reference it (i.e., A::F(x, 3) instead of this->F(x, 3)), it works fine. class A { public: A(void) { }; virtual int F(int x) = 0; protected: int F(int x, int y) { return x + y; } }; class B : public A { public: B(void) { }; virtual int F(int x) { return this->F(x, 3); } }; int main(void) { B b; (void) b.F(3); }
From: Alf P. Steinbach on 13 May 2008 06:12 * nomad: > Anyone have any idea why the code below fails to compile? I get the following > message when I try: > > error C2660: 'B::F' : function does not take 2 arguments.' > > Clearly, B should inherit int F(int, int) from A, the function declaration > is not ambiguous in any way, so it seems to me that I should be able to call > it, yet the compiler refuses to allow me to do it. If I explicitly reference > it (i.e., A::F(x, 3) instead of this->F(x, 3)), it works fine. This is a FAQ (see below). > class A > { > public: > A(void) { }; > virtual int F(int x) = 0; > > protected: > int F(int x, int y) > { > return x + y; > } > }; > > class B : public A > { > public: > B(void) { }; > > virtual int F(int x) > { > return this->F(x, 3); > } > }; > > int main(void) This 'void' is a C-ism. Not that it matters much, just a fine detail. > { > B b; > > (void) b.F(3); This cast is completely unnecessary. > } For your question about why you get a compilation error, see the FAQ item titled "What's the meaning of, Warning: Derived::f(char) hides Base::f(double)?", currently item 23.9, available at e.g. <url: http://www.parashift.com/c++-faq-lite/strange-inheritance.html#faq-23.9>, or any mirror. It's often a good idea to check the FAQ first. Cheers, & hth., - Alf -- A: Because it messes up the order in which people normally read text. Q: Why is it such a bad thing? A: Top-posting. Q: What is the most annoying thing on usenet and in e-mail?
From: nomad on 13 May 2008 06:35 > > (void) b.F(3); > > This cast is completely unnecessary. True, but I like to indicate that I know there's a return value but that I'm explicitly ignoring it. > For your question about why you get a compilation error, see the FAQ > item titled "What's the meaning of, Warning: Derived::f(char) hides > Base::f(double)?", currently item 23.9, available at e.g. <url: > http://www.parashift.com/c++-faq-lite/strange-inheritance.html#faq-23.9>, > or any mirror. Well, I checked the FAQ for inheritance issues, but missed that one. If the compiler had given me a 'derived f(char) hides base::f(double)' error, I'd've known what was going on. I'd forgotten about C++'s silly failure to resolve overloads across scopes. Thanks for the pointer.
From: Alf P. Steinbach on 13 May 2008 07:25 * nomad: >>> (void) b.F(3); >> This cast is completely unnecessary. > > True, but I like to indicate that I know there's a return value but that I'm > explicitly ignoring it. > >> For your question about why you get a compilation error, see the FAQ >> item titled "What's the meaning of, Warning: Derived::f(char) hides >> Base::f(double)?", currently item 23.9, available at e.g. <url: >> http://www.parashift.com/c++-faq-lite/strange-inheritance.html#faq-23.9>, >> or any mirror. > > Well, I checked the FAQ for inheritance issues, but missed that one. If the > compiler had given me a 'derived f(char) hides base::f(double)' error, I'd've > known what was going on. Yes, I notice that neither MSVC nor g++ produce that warning, which would have been good. > I'd forgotten about C++'s silly failure to resolve > overloads across scopes. It's not a failure, it's an intentional design decision. Either way there are (non-obvious) problems, which means that either way the behavior is a little counter-intuitive. The language designer and the committee believed that this design choice minimized the problems, but unfortunately it's also the most counter-intuitive, at least judging from Usenet questions about it... > Thanks for the pointer. You're welcome. Cheers, - Alf -- A: Because it messes up the order in which people normally read text. Q: Why is it such a bad thing? A: Top-posting. Q: What is the most annoying thing on usenet and in e-mail?
From: Vladimir Grigoriev on 13 May 2008 08:56
"nomad" <nomad(a)discussions.microsoft.com> wrote in message news:BA8C8156-5F14-413A-BC1B-E195B94C5A2A(a)microsoft.com... > Anyone have any idea why the code below fails to compile? I get the > following > message when I try: > > error C2660: 'B::F' : function does not take 2 arguments.' > > Clearly, B should inherit int F(int, int) from A, the function declaration > is not ambiguous in any way, so it seems to me that I should be able to > call > it, yet the compiler refuses to allow me to do it. If I explicitly > reference > it (i.e., A::F(x, 3) instead of this->F(x, 3)), it works fine. > > class A > { > public: > A(void) { }; > virtual int F(int x) = 0; > > protected: > int F(int x, int y) > { > return x + y; > } > }; > > class B : public A > { > public: > B(void) { }; > > virtual int F(int x) > { > return this->F(x, 3); > } > }; When the compiler finds the name F it tries resolve it inside the class scope. The class B has only one function with name F which accepts only one parameter. So the compiler signals an error. When you specify explicitly A::F( x, 3 ) the compiler knows which function to use. You can make that the function F with two parameters become visible by including its name in the scope of class B as the following class B: public A { public: virtual int F( int x ) { return this->F( x, 3 ); } protected: using A::F; }; Vladimir Grigoriev |