Monday, June 20, 2005

 

Reflection - Calling Methods using Reflection

To call a method of a type that is retrieved from System.Type, you will use the Invoke() method that is contained in MethodInfo.

object Invoke (object ob, object[] args)

ob is the reference to the object on which the method is invoked. For static method, ob should be null.

args specifies any arguments to be passed to the method. If no arguments, args should be null.
Args must contain exactly the same number of elements as there are arguments.

Here's a sub-program that does that:

Type t = typeof(MyClass);
MyClass reflectOb = new MyClass(10, 20);
int val;

Console.WriteLine("Invoking methods in " + t.Name);
Console.WriteLine();
MethodInfo[] mi = t.GetMethods();

// Invoke each method
foreach (MethodInfo m in mi)
{
ParameterInfo[] pi = m.GetParameters();

if (m.Name == "set" && pi[0].ParameterType == typeof(int))
{
object[] args = new object[2];
args[0] = 9;
args[1] = 18;
m.Invoke(reflectOb, args);
}
}

(From C#: The Complete Reference by Schidlt)
 

Reflection - Getting Method Info

Reflection - obtaining information about a type, comes from the way the reflection process works: A Type object questions and it returns (reflects) the information associated with the type, back to you.

It allows one to learn and use the capabilities of types that are known only at runtime.

Obtaining Information about Members

Once a Type object is obtained, the list of all its methods can be retrived by using the GetMethods() method. It has this form:

MethodInfo[] GetMethods()

It returns an array of MethodInfo objects that describe the methods supported by the invoking type.

Here is a program that uses reflection to obtain the methods supported by a class called MyClass.
using System;
using System.Collections.Generic;
using System.Text;
using System.Reflection;

namespace AnalyzeMethods
{
class MyClass
{
int x;
int y;

public MyClass(int i, int j)
{
x = i; y = j;
}

public int sum()
{
return x + y;
}

public bool isBetween(int i)
{
return (x < i && i < y ) ? true : false;
}
public void set(int a, int b)
{
x = a;
y = b;
}

public void set(double a, double b)
{
x = (int)a;
y = (int)b;
}

public void show()
{
Console.WriteLine("x: {0}, y: {1}", x, y);

}
}

class RelectionDemo
{
static void Main(string[] args)
{
Type t = typeof(MyClass);

Console.WriteLine("Analyzing methods in " + t.Name);
Console.WriteLine();
Console.WriteLine("Methods supported: ");

// 1st way to call
//MethodInfo[] mi = t.GetMethods();

// 2nd way to call
// Only method declared by MyClass are obtained.
MethodInfo[] mi = t.GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Public
| BindingFlags.Instance );

// Dispaly method information
foreach (MethodInfo m in mi)
{
// Display return type and name
Console.Write("\t" + m.ReturnType.Name +
" " + m.Name + "(");

// Display parameters
ParameterInfo[] pi = m.GetParameters();

for (int i = 0; i < pi.Length; i++)
{
Console.Write(pi[i].ParameterType.Name +
" " + pi[i].Name);

if (i + 1 < pi.Length)
Console.Write(", ");
}
Console.WriteLine(")");
}


}
}
}

(Notes obtained from C#: The Complete Reference by Schildt)
 

A simple typeof operator

Just a simple typeof operator:
using System;
using System.IO;

class UseTypeof
{
public static void Main()
{
Type t = typeof(StreamReader);

Console.WriteLine(t.FullName);

if (t.IsClass)
Console.WriteLine("Is a class");
if (t.IsAbstract)
Console.WriteLine("Is abstract");
else
Console.WriteLine("Is concrete.");
}
}

(Taken from C#: The Complete Reference by Schildt)

Result should be:
System.IO.StreamReader
Is a class
Is concrete.

 

Run Type Identification - as operator

If you want to cast an object to another type, but don’t want exceptions to be raised if the cast fails, the as operator is the choice:

expr as type

If the cast succeed: expr will be cast to type type.
If the cast fails: expr will have a null reference.

Here’s an example:
using System;

class A { }
class B : A { }

class CheckCast
{
public static void Main()
{
A a = new A();
B b = new B();

// replace this with
/*
if (a is B)
b = (B)a;
else
b = null;
*/
b = a as B;

if (b == null)
Console.WriteLine("Cast b = (B) a is not allowed.");
else
Console.WriteLine("Cast b = (B) a is allowed.");
}
}

(Taken from the C#: The Complete Reference by Schildt).

The cast will fail, since a is not a B;
 

Runtime Type Identification - is operator

To determine whether an object is of a certain type: we can use the is operator. It will return a boolean result.

expr is type

Returns true if the expression object is of type type or has it derived from type, else it will return false.

This is an example:
using System;

class A { }
class B : A { }

class UseIs
{
public static void Main()
{
A a = new A();
B b = new B();

if (a is A)
Console.WriteLine("a is an A");
if (b is A)
Console.WriteLine("b is an A because it is derived from A");
if (a is B)
Console.WriteLine("Never will be displayed");
else
Console.WriteLine("a is not a B");

if (b is B)
Console.WriteLine("b is a B");
if (a is object)
Console.WriteLine("a is an Object");

}
}

(Taken from C#: The Complete Reference from Herbert Schildt).

The result is
a is an A
b is an A because it is derived from A
a is not a B
b is a B
a is an Object

This page is powered by Blogger. Isn't yours?