Search this site:

2008-01-28

C#: Determining whether a class implements certain interface


Sometimes it is useful to check whether a class (or its instance) implements certain interface. I found a good thread today discussing the issue:

How to determine base interface??? - .NET C#


If you are too busy (well, or too lazy) to dig the answer out of the long page, here is the solution:
typeof(IFoo).IsAssignableFrom(bar.GetType());
typeof(IFoo).IsAssignableFrom(typeof(BarClass));

The Type.IsAssignableFrom() method check whether a type can be assigned from another. It takes a System.Type object as argument, so if you are given a class or an instance of a class, you can use the typeof operator or the Object.GetType() method to get the corresponding System.Type object respectively. The MSDN has a clear definition of the returned value of the IsAssignableFrom() method:
Return Value
Type: System.Boolean

true if c and the current Type represent the same type, or if the current Type is in the inheritance hierarchy of c, or if the current Type is an interface that c implements, or if c is a generic type parameter and the current Type represents one of the constraints of c. false if none of these conditions are true, or if c is a null reference.
As you may have noticed, the IsAssignableForm() method can be applied to all System.Type object, so you can definitely use it to determine whether a class is derived (directly or indirectly) from another. But the case could be more complicated. When you have an interface and a class, the only possible relation is the class (or any class in its class hierarchy) implements the interface. But when you have two classes and try to find out their relation, one could be either the same as, the base or a derivative of another. For the first two case the IsAssignableForm() method returns a true value. Instead of explicitly checking whether two classes being the same, you may use the Type.isSubClassOf() method instead:
typeof(FooClass).isSubClassOf(typeof(BarClass));

Let me use the following examples as a summary:
interface I { /* ... */ }

class A : I { /* ... */ }

class B : A { /* ... */ }

/* something */

Console.WriteLine(
typeof(A).isAssignableFrom(typeof(I))); // false
Console.WriteLine(typeof(A).isSubClassOf(typeof(I))); // false

Console.WriteLine(
typeof(I).isAssignableFrom(typeof(A))); // true
Console.WriteLine(typeof(I).isAssignableFrom(typeof(B))); // true
Console.WriteLine(typeof(B).isSubClassOf(typeof(I))); // false

Console.WriteLine(
typeof(A).isAssignableFrom(typeof(A))); // true
Console.WriteLine(typeof(A).isSubClassof(typeof(A))); // false

Console.WriteLine(
typeof(A).isAssignableFrom(typeof(B))); // true
Console.WriteLine(typeof(A).isSubClassof(typeof(B))); // false

Console.WriteLine(
typeof(B).isAssignableFrom(typeof(A))); // false
Console.WriteLine(typeof(B).isSubClassof(typeof(A))); // true

/* something else */

2008-01-26

Posting codes in Blogger


I have just added some CSS modified from here (in Traditional Chinese) for to make codes looks better in Blogger.

/* .post-body is element in the template i am
currently using, you may want to replace it or
even remove it when applying to your site
*/
.post-body code
{
display
: block; /* fixes a strange IE margin bug */
font-family
: "Courier New", "Monospace";
font-size
: 8pt;
overflow
: auto;
background
: #eee;
border
: 1px solid #ccc;
padding
: 10px 10px 10px 21px;
max-height
: 300px;
max-width
: 100%;
line-height
: 1.2em;
}


Then, put all your codes between <pre><code> and </code></pre> tags. For examples:
<pre><code>foo.bar();</code></pre>


The <code> tags is for CSS styling and the <pre> tag is for preserving white spaces, keeping the indentations. You may wonder why I do not use <pre> tag only, by giving it a class attribute and directly apply CSS style to it, like:
.post-body pre.code  {/* something here */}
and the block likes this:
<pre class="code">foo.bar();</pre>


This should works too, but the reason I prefer the keeping the <code> tag is indeed simple: I would like to keep the semantic meaning for the content.

Just a reminder, you should also do the following replacement to avoid problems, note that the & has to be replaced first:
  • & to &amp;
  • < to &lt;
  • > to &gt;
If you use some code highlighter like the Actipro CodeHighlighter I am using, probably it will help you to handle the conversion too. You may find the service at here and here, it's free.

2008-01-25

Implmentation of Singleton Pattern in C#


When you are talking about programming, a Singleton is a design pattern that address the problem of restricting only one single instance of a class. You can easily find implementations of the pattern from the web. Today when I was working on a programming tasks using C# .NET, I suddenly come up with an idea of having a generic purpose singleton. If you are using .NET Framework 2.0 or above, this can be easily achieved by using generics in C#. However, my program is still using .NET Framework 1.1 so I have to find other ways.

Thanks Chau for working it out with me, here is the solution we got:

public class Singleton
{
// hash table for storing the instances
private static System.Collections.Hashtable _instances = null;

// for thread safety
private static object MUTEX = new object();

// private to prevent instantiation of the class
private Singleton() { }

// overloaded method for convenience
public static object getInstance(System.Type type)
{
return getInstance(type, new object[0]);
}

// get an instance of specified type, the object array is the parameters to constructor
public static object getInstance(System.Type type, object[] parameters)
{
lock(MUTEX)
{
// initialize the internal hash table during the very first call
if (_instances == null)
_instances
= new Hashtable();

// just like ordinary implmentation of singleton, only creates new instance when
// there isn't one yet
if (!_instances.Contains(type))
{
// we need a list of type to get the ConstructorInfo object
System.Type[] types = new Type[parameters.Length];
for (int i=0; i&lt;parameters.Length; i++)
types[i]
= parameters[i].GetType();

// the new instance is created by the following 3 lines of code
System.Reflection.ConstructorInfo constructor = type.GetConstructor(types);
object instance = Activator.CreateInstance(type);
constructor.Invoke(instance, parameters);

// store it for future use
_instances[type] = instance;
}

return _instances[type];
}
}
}


You can then use it like this:
SomeClass c = (SomeClass) Singleton.getInstance(typeof(SomeClass));


Someone may argue that this is not really a singleton, because one may still instantiate the class directly using its constructors. Strictly speaking yes. So this should only be a workaround, that to those classes can only be initiated once through this object. Maybe I really shouldn't name it a singleton... Anyway, please let it be until I got some other ideas.

Comments are welcome, thanks! Since the codes are simple and the main purpose is only to illustrate the idea, I would like to put it into the public domain, just use it freely if you find it useful. :)

Codes are highlighted by Actipro CodeHighlighter.

A software a day


This site lets you freely download licensed software everyday (legally), and each download only available for exactly 24 hours:

Giveaway of the day: free licensed software daily

Although you may not have heard of those software listed, but if you are geeks that keen on finding/testing useful software, this is a site for you. It could also be a great platform for software vendors to attract more users. Read here for more information.

Special notes:

  1. You need to install the software before the free download offer expires. It is because the version downloaded from there is inside a special container that verifies the Giveaway offer is still valid. Therefore, at least unpack from the special container once you downloaded the package.
  2. The softwares downloaded there usually have no free upgrade, no free technical support and is restricted to non-commercial use only.

2008-01-23

Java: pass by reference or value?


Does Java pass function arguments by reference or value?

This is a confusing question. There are tons of people arguing this on the web. Here is my comment:

  • Java passes function arguments by value
  • Java handles object with object reference
So, when Java passes objects into function, it actually passes the object references. Object references is nothing special to other types, they are passed into function by values. That is, in short, Java passes object reference by value.

If you want to know more, read this very good article explaining the problem clearly with codes and graphical examples.

2008-01-09

ERROR: Expansion ROM not initialized - PCI on Motherboard


Starting from yesterday I got the following messages when I boot up my Thinkpad T60:

Initializing Intel(R) Boot Agent GE v1.2.31

PXE-E05: The LAN adapter's configuation is corrupted or has not been initialized. The Boot Agent cannot continue.

After a while I got this:
ERROR
Expansion ROM not initialized - PCI on Motherboard
Bus:00, Device:00, Function:00

Press [ESC] to continue

After I pressed ESC, everything looks normal, but there must be something goes wrong.

Having a search in Google, someone suggested to disable the internal network option ROM option in the BIOS, but this is obviously only a workaround. There is a discussion thread related to the issue, haven't read it yet.

Quite busy now, let me deal with it later.

2008-01-21 Updates:
Forget to mention, I have followed the instructions here: disabling the "Read Network ROM on Startup" under "Config/Networking" in the BIOS. Saved the settings and restarted, the message was gone, and the Ethernet card is still working. This should be just a workaround as I *thought* (yes, thought only) this setting was enabled since I get this notebook and got no problem. Has anyone contacted Lenovo support? What's their official explanation to the problem?

Disclaimer

ALL CONTENTS AND INFORMATION IN THIS WEB SITE ARE PROVIDED "AS IT" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED. THE ACCURACY AND AVAILABILITY OF THE CONTENTS, INFORMATION AND THE WEB SITE ITSELF ARE NOT GUARANTEED. THE AUTHOR TAKES NO RESPONSIBILITIES ON ANY COSTS OR DAMAGES (DIRECT OR INDIRECT) ARISING OUT OF OR IN CONNECTION WITH THE ACCESS, USAGE OR INABILITY OF USAGE OF THIS WEB SITE.