πŸš€ go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: borland.public.csharpbuilder.language.csharp
Article #143

Re: More about "class of" in C#

#143
From: David Fallas
Date: Fri, 22 Jun 2007 01:02
152 lines
5252 bytes
For the sake of completeness for anyone referring to this thread in future - 
there is a little bit more to the story if using the first strategy 
suggested.

Where there is a requirement to call a static method which has NOT been 
overridden in a descendent class, the type.GetMethod() method will not find 
it (where type is the descendent's type).

Instead, if it isn't known if the method has been overridden or not, one 
needs to check the return from the type.GetMethod("xxxx") call and if null, 
call type.BaseType.GetMethod("xxxx") to find the base class' implementation 
of the method.

This appears to differ significantly from Delphi which seems to be capable 
of finding either a base or overridden method quite happily.
"Joanna Carter [TeamB]" <joanna@nospam.for.me> wrote in message 
news:4677b67f@newsgroups.borland.com...
> Borland a οΏ½crit :
>
>> Referring to that posting from December last year re "class of"... I 
>> understand the use of Activator.CreateInstance(ClassType) as a 
>> replacement for the Delphi "class of" for use in a C# abstract class 
>> factory, but how would I use that ClassType reference to call a static 
>> method (eg public static DoIt()) which has been declared in the Class 
>> class?
>>
>> In Delphi I would simply retrieve the "class of" reference, (eg 
>> ClassClass - class of TClass), and call the function normally - eg 
>> TClass(ClassClass).DoIt;
>
> First, can I ask you to change your posting name from Borland ?
>
> Now, to the matter in hand.
>
> Don't forget that, in C#, static methods cannot be virtual. Therefore, you 
> have to redlclare the method in each and every derived class but simply 
> calling the static method on the base type will only call that method, not 
> the derived one.
>
> However, here is a simple example fo how to create a factory class that 
> will call the correct method, depending on the type passed in.
>
>   public class Base
>   {
>     public static void DoIt(int arg) { }
>   }
>
>   public class Derived : Base
>   {
>     public static void DoIt(int arg) { }
>   }
>
>   public static class Factory
>   {
>     public static void DoIt(Type type, int arg)
>     {
>       if (!typeof(Base).IsAssignableFrom(type))
>         throw new Exception("Type must derive from Base");
>
>       Type[] argTypes = new Type[] { typeof(int) };
>
>       MethodInfo mi = type.GetMethod("DoIt", argTypes);
>
>       object[] args = new object[] { arg };
>
>       mi.Invoke(null, args);
>     }
>   }
>
>     private void button1_Click(object sender, EventArgs e)
>     {
>       Type type = typeof(Derived);
>
>       Factory.DoIt(type, 123);
>     }
>
> You can also use the idea of a metaclass to achieve a more Delphi-like 
> syntax.
>
>   public class Base
>   {
>     #region metaclass
>
>     public class ClassReference
>     {
>       #region private members
>
>       private Type internalType;
>
>       #endregion
>
>       public void DoIt(int value)
>       {
>         MethodInfo methodInfo = internalType.GetMethod("DoIt", 
> BindingFlags.Public | BindingFlags.Static);
>
>         object[] args = new object[] { value };
>
>         methodInfo.Invoke(null, args);
>       }
>
>       #endregion
>
>       #region constructors
>
>       // default constructor
>       private ClassReference(Type type)
>       {
>         internalType = type;
>       }
>
>       #endregion
>
>       #region implicit conversion operator
>
>       public static implicit operator ClassReference(Type input)
>       {
>         if (!typeof(Shape).IsAssignableFrom(input))
>           throw new ArgumentException(String.Format("Type {0} must derive 
> from {1}", input.Name, typeof(Base).Name), "input");
>
>         return new ClassReference(input);
>       }
>
>       #endregion
>     }
>
>     #endregion
>
>     public static void DoIt(int value) {...}
>   }
>
>   public class Derived : Base
>   {
>     public static void DoIt() {...}
>   }
>
> This then allows the following calling syntax :
>
>   {
>     Base.ClassReference classRef = typeof(Derived);
>
>     classRef.DoIt(123);
>   }
>
> Is that what you are looking for ?
>
> Joanna
>
> -- 
> Joanna Carter [TeamB]
> Consultant Software Engineer 
Technical Details
Message-ID: <467b1fbe$1@newsgroups.borland.com>
Path: arc1-ca.pugleaf.net!g2news1.google.com!news2.google.com!news1.google.com!news.glorb.com!newsfeeds.ihug.co.nz!ihug.co.nz!newsgroups.borland.com!not-for-mail
References: <467757d6$1@newsgroups.borland.com> <4677b67f@newsgroups.borland.com>

Show Full Headers
Complete Article Headers
X-Google-Thread: 1efe35,77a80b77cf3a9a3e
X-Google-Attributes: gid1efe35,public,usenet
X-Google-Language: ENGLISH,ASCII
From: "David Fallas" <fallasd@sysmex.co.nz>
Newsgroups: borland.public.csharpbuilder.language.csharp
References: <467757d6$1@newsgroups.borland.com> <4677b67f@newsgroups.borland.com>
Subject: Re: More about "class of" in C#
Date: Fri, 22 Jun 2007 13:02:40 +1200
Lines: 154
X-Priority: 3
X-MSMail-Priority: Normal
X-Newsreader: Microsoft Outlook Express 6.00.2900.2869
X-RFC2646: Format=Flowed; Response
X-MimeOLE: Produced By Microsoft MimeOLE V6.00.2900.2962
NNTP-Posting-Host: 210.55.97.206
Message-ID: <467b1fbe$1@newsgroups.borland.com>
X-Trace: newsgroups.borland.com 1182474174 210.55.97.206 (21 Jun 2007 18:02:54 -0700)
Path: arc1-ca.pugleaf.net!g2news1.google.com!news2.google.com!news1.google.com!news.glorb.com!newsfeeds.ihug.co.nz!ihug.co.nz!newsgroups.borland.com!not-for-mail