473,587 Members | 2,492 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

Derived classes and overloaded methods

The output of this simple program below differs if it's compiled in
Visual Studio 2005 and 2008. Is one the correct output, and if so,
why?

using System;

namespace DerivedTestApp
{
class BaseClass
{
static public void Test(uint a)
{
Console.WriteLi ne("(BaseClass ) uint: {0}", a);
}
}

class DerivedClass : BaseClass
{
public enum TestEnum
{
Alpha,
Beta,
}

static public void Test(TestEnum a)
{
string s = "Error";
switch (a)
{
case TestEnum.Alpha: s = "Alpha"; break;
case TestEnum.Beta: s = "Beta"; break;
}
Console.WriteLi ne("(DerivedCla ss) TestEnum: {0}", s);
}
}

class Program
{
static void Main()
{
DerivedClass.Te st((uint)0);
DerivedClass.Te st(DerivedClass .TestEnum.Alpha );
}
}
}

// -- Visual studio 2005:
//(BaseClass) uint: 0
//(DerivedClass) TestEnum: Alpha
// -- Visual studio 2008:
//(DerivedClass) TestEnum: Alpha
//(DerivedClass) TestEnum: Alpha
Jun 27 '08 #1
7 2304
On Fri, 25 Apr 2008 10:37:39 -0700, <Ra**********@g mail.comwrote:
The output of this simple program below differs if it's compiled in
Visual Studio 2005 and 2008. Is one the correct output, and if so,
why?
It's a known "breaking change" for VS2008. See
http://download.microsoft.com/downlo...udio_2008.docx

The short answer is (from the above document): "All constant expressions
equal to 0 are now implicitly convertible to enum types"

In other words, even though you cast your 0 to "uint", the compiler is
able to implicitly convert it to an enum type. Since you're calling the
method from the derived class, the compiler prefers the overload found in
that class, and since it can implicitly convert the 0 to the appropriate
enum type now, it does.

Pete
Jun 27 '08 #2
On Apr 25, 10:45*am, "Peter Duniho" <NpOeStPe...@nn owslpianmk.com>
wrote:
On Fri, 25 Apr 2008 10:37:39 -0700, <Random.Co...@g mail.comwrote:
The output of this simple program below differs if it's compiled in
Visual Studio 2005 and 2008. *Is one the correct output, and if so,
why?

The short answer is (from the above document): "All constant expressions *
equal to 0 are now implicitly convertible to enum types"
Thanks!

Jun 27 '08 #3
On Apr 25, 1:45 pm, "Peter Duniho" <NpOeStPe...@nn owslpianmk.com>
wrote:
On Fri, 25 Apr 2008 10:37:39 -0700, <Random.Co...@g mail.comwrote:
The output of this simple program below differs if it's compiled in
Visual Studio 2005 and 2008. Is one the correct output, and if so,
why?

It's a known "breaking change" for VS2008. See http://download.microsoft.com/downlo...789-411c-a367-...

The short answer is (from the above document): "All constant expressions
equal to 0 are now implicitly convertible to enum types"

In other words, even though you cast your 0 to "uint", the compiler is
able to implicitly convert it to an enum type. Since you're calling the
method from the derived class, the compiler prefers the overload found in
that class, and since it can implicitly convert the 0 to the appropriate
enum type now, it does.

Pete
will the same difference be reflected in overloaded functions with
int some1(SomeEnum a)
int some1(uint a)
Jun 27 '08 #4
On Fri, 25 Apr 2008 12:56:10 -0700, parez <ps*****@gmail. comwrote:
will the same difference be reflected in overloaded functions with
int some1(SomeEnum a)
int some1(uint a)
I'm not sure what you're asking. What's the difference between that and
the OP's question? Do you mean if the methods are both in the same
class? If so, I think the answer is "yes".

In fact, reviewing the overload resolution rules, I think I might have
been misstating the rule to say that a method in a more-derived class has
precedence. I didn't see a rule in the C# 3.0 spec that says that.
However, it _does_ say that a more-specific type takes precedence over a
less-specific type. That's probably the rule at work here -- the enum is
more specific than the uint -- and that rule would apply whether the
methods are declared in the same class, or in different classes within the
inheritance hierarchy.

Pete
Jun 27 '08 #5
Peter Duniho <Np*********@nn owslpianmk.comw rote:
In fact, reviewing the overload resolution rules, I think I might have
been misstating the rule to say that a method in a more-derived class has
precedence.
It's somewhat buried. Basically if an applicable method is *first
declared* (i.e. not overridden) in a more derived class, *all*
applicable methods first declared in base classes are ignored. It leads
to very unintuitive cases, such as this:

using System;

class Base
{
public virtual void Foo(int x)
{
Console.WriteLi ne("Base.Foo(in t)");
}
}

class Derived : Base
{
public override void Foo(int x)
{
Console.WriteLi ne("Derived.Foo (int)");
}

public void Foo(object x)
{
Console.WriteLi ne("Derived.Foo (object)");
}
}

class Test
{
static void Main()
{
new Derived().Foo(1 );
}
}

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
World class .NET training in the UK: http://iterativetraining.co.uk
Jun 27 '08 #6
On Sat, 26 Apr 2008 13:20:21 -0700, Jon Skeet [C# MVP] <sk***@pobox.co m>
wrote:
Peter Duniho <Np*********@nn owslpianmk.comw rote:
>In fact, reviewing the overload resolution rules, I think I might have
been misstating the rule to say that a method in a more-derived class
has
precedence.

It's somewhat buried. Basically if an applicable method is *first
declared* (i.e. not overridden) in a more derived class, *all*
applicable methods first declared in base classes are ignored. It leads
to very unintuitive cases, such as this: [snip]
Ahh...so I wasn't just imagining things. And yes, I agree that the
example you showed isn't completely intuitive. I do kind of understand
why the rule is the way it is. But it's not immediately obvious why it
makes sense that the hierarchy-based rule takes precedence over the "more
specific type" rule.

Anyway, thanks for the clarification. Good stuff. :)

Pete
Jun 27 '08 #7
Peter Duniho <Np*********@nn owslpianmk.comw rote:
It's somewhat buried. Basically if an applicable method is *first
declared* (i.e. not overridden) in a more derived class, *all*
applicable methods first declared in base classes are ignored. It leads
to very unintuitive cases, such as this: [snip]

Ahh...so I wasn't just imagining things. And yes, I agree that the
example you showed isn't completely intuitive. I do kind of understand
why the rule is the way it is.
I understand it when there *isn't* an override in the derived class
(otherwise you have a versioning issue if a base class adds an overload
unexpectedly) but when there *is* an override, it's clear that the
derived class knows about the base class's method, so at that point I
see no reason to exclude that signature.
But it's not immediately obvious why it makes sense that the
hierarchy-based rule takes precedence over the "more specific type"
rule.
Right.
Anyway, thanks for the clarification. Good stuff. :)
I'm just glad you haven't asked me where it is in the spec. It's
definitely there somewhere, but it always takes me a while to find!

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
World class .NET training in the UK: http://iterativetraining.co.uk
Jun 27 '08 #8

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

24
1728
by: Brad Marts | last post by:
I would like to have a function that takes as an argument a base class but performs differently depending on which type of derived class is passed. Can I tell which derived class is passed? For example: class Base { //... };
7
8653
by: Tron Thomas | last post by:
Under the right compiler the following code: class Base { public: virtual void Method(int){} }; class Derived: public Base {
1
1725
by: Jose | last post by:
Hello: I'm preparing a multitier application, and in the Data Layer I have a EmployeeRepositoryBase class that has a protected static method called Fill() and some GetAll() overloaded protected static methods. All GetAll() static methods call the same Fill() in the base class. When I want to make a new derived class EmployeeRepository from...
9
1791
by: Larry Woods | last post by:
I have a method in my base class that I want ALL derived classes to use. But, I find that I can create a "Shadow" method in my derived class that "overrides" the method in my base class. Can't figure out what attribute to put on the base class method to prevent this. TIA, Larry Woods
8
18530
by: Manuel | last post by:
Hi! If I've a vector filled with abstract classes, can I push in it the derived classes too? Even if derived classes have new methods? I've done some experiments, and it seem I can push the derived classes, but I can use them only calling the methods declared in abstract class (the new methods declared only in derived classes return an...
15
2140
by: Jeff Mason | last post by:
Hi, I'm having a reflection brain fog here, perhaps someone can set me on the right track. I'd like to define a custom attribute to be used in a class hierarchy. What I want to do is to have an attribute which can be applied to a class definition of a class which inherits from a base, mustinherit class. I want to define methods in the...
11
3037
by: Aflj | last post by:
This code won't compile (two compilers tried, gcc and VC++, both of recent versions, but I don't remember them exactly): class C1 { public: void M1(int i) {} }; class C2: public C1
12
2851
by: bgold | last post by:
Hey. I have a base class (SPRITE), and using this base class I have derived a large number of derived classes (PERSON, BULLET, MISSILE, etc.). Now, at a certain point in my program, I have a pair of pointers, where each is a pointer to the base class (each is a SPRITE *). I know that each of these pointers actually points to one of the...
5
3180
by: Fokko Beekhof | last post by:
Hello all, please consider the following code: -------------------------------------------------- #include <tr1/memory> struct BaseA { int x;
0
8215
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. ...
0
8347
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that...
1
7973
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For...
0
6626
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then...
1
5718
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupré who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes...
0
3844
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in...
0
3879
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
1
2358
by: 6302768590 | last post by:
Hai team i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system
1
1454
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.