471,334 Members | 1,398 Online
Bytes | Software Development & Data Engineering Community
Post +

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 471,334 software developers and data experts.

Can I get the class name in a static method or property


If I have an object I know I can get the name of the class but can I get the class name in the following scenario :

public class ParentClass
{
public static string ClassName
{
get
{
return "ParentClass"
}

}
}
public class ChildClass : ParentClass
{

}
So that ChildClass.ClassName returns "ChildClass" and ParentClass.ClassName returns "ParentClass"

It may seem a bit strange but I really want to use it to return a token based on the class name that can be used for reading data
from an xml file and that contains a list of these classes.

I would like to be able to base the read on just knowing the class name and not have to store static data in each class which could
be calculated from the class name.

So, I will be able to write

MyStoredData.GetData(ChildClass.ClassName) and it will return all the records in the xml of type ChildClass and MyStoredData
encapsulates the reading of data and GetData is a static method
It is not important whether I get the class name from a method or a property.

Any ideas welcome. Hope it makes sense.

Steve
Sep 2 '08 #1
10 1658
The cleanest answer I can suggest is generics - have GetData<T>(), so
you call GetData<ChildClass>(), then inside GetData<T>() you can use
typeof(T).Name, or access attribute metadata from typeof(T) such as
XmlTypeAttribute.

Marc
Sep 2 '08 #2
steve <s_******@yahoo.comwrote:
>
If I have an object I know I can get the name of the class
but can I get the class name in the following scenario :

public class ParentClass
{
public static string ClassName
{
get
{
return "ParentClass"
}

}
}
public class ChildClass : ParentClass
{

}
So that ChildClass.ClassName returns "ChildClass"
and ParentClass.ClassName returns "ParentClass"
No, you can't do this. In fact, if you look at the generated code for
"ChildClass.ClassName" you'll see it's *actually* a call to
"ParentClass.ClassName".
It may seem a bit strange but I really want to use it to return a
token based on the class name that can be used for reading data from
an xml file and that contains a list of these classes.

I would like to be able to base the read on just knowing the class
name and not have to store static data in each class which could be
calculated from the class name.

So, I will be able to write

MyStoredData.GetData(ChildClass.ClassName) and it will return all the
records in the xml of type ChildClass and MyStoredData encapsulates
the reading of data and GetData is a static method

It is not important whether I get the class name from a method or a
property.

Any ideas welcome. Hope it makes sense.
Could you change to use generics instead?

MyStoredData.GetData<ChildClass>(...)

?

--
Jon Skeet - <sk***@pobox.com>
Web site: http://www.pobox.com/~skeet
Blog: http://www.msmvps.com/jon.skeet
C# in Depth: http://csharpindepth.com
Sep 2 '08 #3
On Tue, 02 Sep 2008 13:33:25 -0700, steve <s_******@yahoo.comwrote:
[...]
So that ChildClass.ClassName returns "ChildClass" and
ParentClass.ClassName returns "ParentClass"
Since you cannot call the static member (method or property) without
knowing the class name already, how would this benefit you? How is
writing this:

MyStoredData.GetData(ChildClass.ClassName);

better than this:

MyStoredData.GetData("ChildClass");

or even:

MyStoredData.GetData(typeof(ChildClass).GetName()) ;

?

More generally, while it's not your question specifically, .NET already
has serialization support built in, including being able to serialize to
an XML file. It sounds a little like you might be reinventing the wheel
here.

Pete
Sep 2 '08 #4

It helps me because I do not use the class name. I manipulate it to give me an xml token which is based on the class name and I
would have to include this logic in all the methods that need to create the token.

I wrote xml read routine a long time ago. I didn't know about the serialization stuff at that time - or if it existed. But, anyway
the class has a lot of variables which are not always used but I have logic in my read/write routines to allow me to ignore writing
data based on the values in certain fields. I am not sure I could have done this with the serialization that is in the Xml
namespace. It saves me an awful lot of space in the output xml file.

I realized that I did have a ChildClass object around when I was making the call so I made them non-static. I guess I could have
created a static conversion routine and hidden that in the parent class.

I will take a look at the generics stuff.

Thanks to all,
Steve

On Tue, 02 Sep 2008 14:00:05 -0700, "Peter Duniho" <Np*********@nnowslpianmk.comwrote:
>On Tue, 02 Sep 2008 13:33:25 -0700, steve <s_******@yahoo.comwrote:
>[...]
So that ChildClass.ClassName returns "ChildClass" and
ParentClass.ClassName returns "ParentClass"

Since you cannot call the static member (method or property) without
knowing the class name already, how would this benefit you? How is
writing this:

MyStoredData.GetData(ChildClass.ClassName);

better than this:

MyStoredData.GetData("ChildClass");

or even:

MyStoredData.GetData(typeof(ChildClass).GetName()) ;

?

More generally, while it's not your question specifically, .NET already
has serialization support built in, including being able to serialize to
an XML file. It sounds a little like you might be reinventing the wheel
here.

Pete
Sep 2 '08 #5
On Tue, 02 Sep 2008 15:43:16 -0700, steve <s_******@yahoo.comwrote:
It helps me because I do not use the class name. I manipulate it to give
me an xml token which is based on the class name and I
would have to include this logic in all the methods that need to create
the token.
Or, you could just create a single static method somewhere that does that
transformation for you, based on an explicitly-given class name. That
logic doesn't have to be in the class, and it might even be more
appropriate for it _not_ to be there (depending on how you've encapsulated
the serialization logic).

If not in the type you're serializing, it could even be an extension
method, either on the Type or String class (depending on what syntax you
prefer).
I wrote xml read routine a long time ago. I didn't know about the
serialization stuff at that time - or if it existed. But, anyway
the class has a lot of variables which are not always used but I have
logic in my read/write routines to allow me to ignore writing
data based on the values in certain fields. I am not sure I could have
done this with the serialization that is in the Xml
namespace. It saves me an awful lot of space in the output xml file.
I get the various serialization types mixed up, so I can't tell you which
one specifically I've used more (such as it is...I don't write a lot of
serialization code). But I can tell you that the one I've used more
allows all sorts of customization and control over the serialization.

Pete
Sep 2 '08 #6
I am not sure I could have done this with the serialization that is in the Xml
namespace. It saves me an awful lot of space in the output xml file.
Sure you can... for the simple cases you can just specify
[DefaultValue(...)]; for more complex cases you just add a bool
ShouldSerialize{prop-name}() method. This method pattern is inherited
from System.ComponentModel, where it works even if private, but IIRC
XmlSerializer likes the method to be public (you can always hide it
from intellisense with EditorBrowsableAttribute). Finally, for the
most extreme cases you can implement IXmlSerializable (although this
largely defeats the point).

If you are talking about whitespace etc, then XmlWriterSettings is
what you want.

Marc
Sep 3 '08 #7

I have been looking at the book "Beginning XML with C# 2008" by Joshi and I can't see anything that would allow me to do what I want
or what you suggest.

A typical example would be writing out a Polygon class where I can give a different color to each edge of the polygon. But, in the
majority of cases all the edges will be the same color or not drawn so that if I write out a node or attribute indicating the edges
do not need to be drawn I know I don't need to write out the attributes for each of the sides.

Also multiple classes get written to the same xml file. Would that be a problem for the serializer?

If you know of a good source to read about this it would be appreciated.

Thanks,
Steve


On Tue, 2 Sep 2008 23:16:11 -0700 (PDT), Marc Gravell <ma**********@gmail.comwrote:
>I am not sure I could have done this with the serialization that is in the Xml
namespace. It saves me an awful lot of space in the output xml file.

Sure you can... for the simple cases you can just specify
[DefaultValue(...)]; for more complex cases you just add a bool
ShouldSerialize{prop-name}() method. This method pattern is inherited
from System.ComponentModel, where it works even if private, but IIRC
XmlSerializer likes the method to be public (you can always hide it
from intellisense with EditorBrowsableAttribute). Finally, for the
most extreme cases you can implement IXmlSerializable (although this
largely defeats the point).

If you are talking about whitespace etc, then XmlWriterSettings is
what you want.

Marc
Sep 3 '08 #8
Also multiple classes get written to the same xml file. Would that be a problem for the serializer?

As long as they are expected, for example via XmlIncludeAttribute for
sub-types
If you know of a good source to read about this it would be appreciated.
msdn:
http://msdn.microsoft.com/en-us/library/83y7df3e.aspx
http://msdn.microsoft.com/en-us/library/2baksw0z.aspx
http://msdn.microsoft.com/en-us/library/athddy89.aspx

I can't find a good source for ShouldSerialize, but it works: in the
following, Foo is written, Bar isn't:

using System;
using System.ComponentModel;
using System.Xml.Serialization;

[Serializable, XmlType("test")]
public class Test
{
[XmlAttribute("foo")]
public string Foo { get; set; }
[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeFoo() { return true; }
[XmlAttribute("bar")]
public string Bar { get; set; }
[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeBar() { return false; }
}

static class Program
{
static void Main()
{
XmlSerializer xser = new XmlSerializer(typeof(Test));
Test obj = new Test { Foo = "abc", Bar = "def" };
xser.Serialize(Console.Out, obj);
}
}
Sep 3 '08 #9
(obviously the ShouldSerialize methods would normally check some other
state to make the decision - for a more interesting example, consider
a rectangle that serializes @width and @height if non-square, and
@size otherwise):

using System;
using System.ComponentModel;
using System.Xml.Serialization;

[Serializable, XmlType("rectangle")]
public class Rectangle
{
[XmlAttribute("width")]
public int Width { get; set; }
[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeWidth() { return Width != Height; }

[XmlAttribute("height")]
public int Height { get; set; }
[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeHeight() { return Width != Height; }

[XmlAttribute("size")]
public int Size {
get {
if (Width == Height) return Width;
throw new InvalidOperationException("Size only valid for
squares");
}
set {Width = Height = value;}
}

[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeSize() { return Width == Height; }
}

static class Program
{
static void Main()
{
XmlSerializer xser = new XmlSerializer(typeof(Rectangle));
Rectangle rect = new Rectangle { Width = 2, Height = 3 };
xser.Serialize(Console.Out, rect);
rect.Width = 3; // should now be square
xser.Serialize(Console.Out, rect);
}
}
Sep 3 '08 #10

Thanks for the examples. I can play around with it and see how I can get it to work for what I am doing.

Steve


On Wed, 3 Sep 2008 04:40:51 -0700 (PDT), Marc Gravell <ma**********@gmail.comwrote:
>(obviously the ShouldSerialize methods would normally check some other
state to make the decision - for a more interesting example, consider
a rectangle that serializes @width and @height if non-square, and
@size otherwise):

using System;
using System.ComponentModel;
using System.Xml.Serialization;

[Serializable, XmlType("rectangle")]
public class Rectangle
{
[XmlAttribute("width")]
public int Width { get; set; }
[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeWidth() { return Width != Height; }

[XmlAttribute("height")]
public int Height { get; set; }
[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeHeight() { return Width != Height; }

[XmlAttribute("size")]
public int Size {
get {
if (Width == Height) return Width;
throw new InvalidOperationException("Size only valid for
squares");
}
set {Width = Height = value;}
}

[EditorBrowsable(EditorBrowsableState.Never)]
public bool ShouldSerializeSize() { return Width == Height; }
}

static class Program
{
static void Main()
{
XmlSerializer xser = new XmlSerializer(typeof(Rectangle));
Rectangle rect = new Rectangle { Width = 2, Height = 3 };
xser.Serialize(Console.Out, rect);
rect.Width = 3; // should now be square
xser.Serialize(Console.Out, rect);
}
}
Sep 3 '08 #11

This discussion thread is closed

Replies have been disabled for this discussion.

Similar topics

1 post views Thread by Phil Powell | last post: by
1 post views Thread by Phil Powell | last post: by
2 posts views Thread by Stan | last post: by
reply views Thread by Ed West | last post: by
6 posts views Thread by Davinci_Jeremie | last post: by
13 posts views Thread by Liz | last post: by
49 posts views Thread by Ben Voigt [C++ MVP] | last post: by
reply views Thread by rosydwin | last post: by

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.