Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations strongm on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Reflection - Assembly Question 1

Status
Not open for further replies.

23maploosh

Programmer
Mar 9, 2009
5
CA
I am trying to understand the concept of reflection and found a tutorial on the web. I thought I understood it until I started to play with it a little further. I created a winform app named 'reflectiontesting'. I also created a simple class called 'clsCar' that simply overrides the toString() method and displays 'I am a car'. I have two buttons on the form. The first buttons loops through all of the assemblies in the current app domain and simply prints out their type. Here is the code:

foreach (Assembly assem in AppDomain.CurrentDomain.GetAssemblies())
{
MessageBox.Show(assem.ToString());
}

The second button creates an instance of the Car class and then calls its toString method. Here is the code for that.
System.Reflection.Assembly assem = System.Reflection.Assembly.Load("ReflectionTesting");
Object c = assem.CreateInstance("reflectionTesting.clsCar");
MessageBox.Show(c.ToString());

After running and playing with this code I thought I started to understand the concept. I then went into my debug directory for this assembly and renamed the executable to 'reflectiontesting99.exe'. Once I did this and clicked button2 I received a FileNotFound Exception. I then clicked button1 and it showed that the assembly ReflectionTesting was still loaded.
I am just wondering why changing the executable name after it has been produced causes this error?
Thanks
Matt
 
I think we need more information before we can comment. I can't see where you explain what button2 does, so it's tough to figure out why you get the exception there. Can you elaborate on what button2 does and provide code that causes the error?
 
In my question I show the code under button2. Here is the code again:

System.Reflection.Assembly assem = System.Reflection.Assembly.Load("ReflectionTesting");
Object c = assem.CreateInstance("reflectionTesting.clsCar");
MessageBox.Show(c.ToString());

All I did was hard code to load assembly ReflectionTesting and then I create an instance of the clsCar class and call its toString() method that simply displays something like "I am a Car".

I just do not understand why this code causes an exception when I change the .exe name and then run it because even with the .exe name change button1 still shows the assembly named reflectionTesting. I hope this is a little more descriptive.
Thanks
Matt
 
Sorry, I missed it! Ok, I see what you are up to. There is a lot of information being kept for an assembly. If you look at the properties of your reflectiontest99.exe file, you'll see that there's an internal name property, and I'll bet that it still says ReflectionTest. Furthermore, looking up the Load method, it says that the string argument is a long name. Since you're using a simple name, the long name has to be inferred. I suspect that the loader probes the assemblies, looking for an internal name "reflectiontest99", and fails to find one because the name is still "ReflectionTest". This would be the first thing I tested. (Sorry I'm not in a position to test it myself, don't have a copy of C# at work that's easily accessible.)

This is an explanation of how assemblies are loaded: Now, the first button simply gets the assemblies and looks up the internal name. To get a better handle on the assembly object, you might think about redoing this code as a console application. Instead of using a form, buttons, and MessageBox.Show, you'll use Console.Write. Then you'll run your application from the command prompt.

You can experiment with getting the assemblies and listing out all the properties. I'd start with something like this (assuming you're using a console application):
Code:
        Console.WriteLine("Assembly Full Name:");
        Console.WriteLine(assem.FullName);
Which I of course stole from the Microsoft doc. Then you can look at other properties, and I feel pretty sure you'll find an exact answer to your problem. Please publish it when you do!

HTH

Bob
 
I think I may understand why I am getting this error now. First of all thanks BobRodes for the help. I believe what is happening is when I rename the assembly and then click button2:
System.Reflection.Assembly assem = System.Reflection.Assembly.Load("ReflectionTesting");
Object c = assem.CreateInstance("reflectionTesting.clsCar");
MessageBox.Show(c.ToString());

The assembly looks in directory where it was run from and then tries to load the ReflectionTesting assembly but since I renamed it to ReflectionTesting99 it cannot find it. After realizing this instead of renaming the assembly I copied it and then renamed the copy to ReflectionTesting99. I then ran the ReflectionTesting99 assembly and it worked fine because the ReflectionTesting assembly still exists.


 
I could have sworn that I saw this line:
Code:
System.Reflection.Assembly assem = System.Reflection.Assembly.Load("ReflectionTesting");
as this:
Code:
System.Reflection.Assembly assem = System.Reflection.Assembly.Load("ReflectionTesting99");
Ok. It will be interesting for you to rename the file to reflectiontesting99.exe and then try to load it using that name. If that does work, then we know that the Load method is looking for the name of the exe file. Now, if you run GetAssemblies against reflectiontesting99.exe and the type name comes up ReflectionTesting, then it means that the assembly's internal name is one thing, and its exe file name is another.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top