473,587 Members | 2,496 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

Making the correct class at runtime based on loaded data

I hav been looking for the last 2 hours on how to do this without much luck.

Im going to give a simplifed model of the problem i have.

I want a collection class that can holds a series or objects, for arguments
sake, lets make these fruit :
apple
orange
bannana
in my application i have

public abstract class Fruit

{

float m_Weight = 0.0f;

public void setweight(float weight)

}

public class Apple : Fruit

{

}

public class Orange : Fruit

{

}

public class Bannana : Fruit

{

}
What i want to implement is a collection class that can hold a series of
items.

ArrayList theFruit = new ArrayList();

Now i want to open a file

pseudocode :

Openthefile(fru ity.txt)
{
foreach line in the file
{
find the correct object type
create that object type
add the data to it
add it to the collection class
}
}

Now the file will contain a list something like this, i.e. a random list of
fruit.

Type, Weight
Bannana 1.03
Apple 2.12
Pear 4.23
Bannana 5.34
Bannana 1.22
Apple 3.33
How do i make the collection class contain objects of the correct type at
runtime ????

Many Thanks for anyones help
Jon Rea
Nov 15 '05 #1
9 1446
Jon Rea <jr****@bris.ac .uk> wrote:
I hav been looking for the last 2 hours on how to do this without much luck.

Im going to give a simplifed model of the problem i have.


<snip>

Assuming they all have the same properties, the way to do it is:

o Use Type.GetType to get the type listed in the file.
o Check that the type has actually been found (i.e. Type.GetType hasn't
returned null).
o Use Activator.Creat eInstance to create an instance of the type.
o Cast the returned reference to the base type (Fruit in your example)
o Call SetWeight etc with the rest of the data in the line.

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 15 '05 #2
Jon,

There are design patterns that cover this sort of thing. Depending on the
details of your scenario, you might find either the abstract factory or the
factory method to be applicable (see
http://www.dofactory.com/patterns/Patterns.aspx for some C# examples).

However, if you feel this is too complex, and your situation is really as
simple as you present (and your pear is really meant to be an orange <g>), a
simple switch on the name found in the file should do the trick. e.g.:

<foreach line in the file>
{
Fruit newFruit = null;

string fruitName = <the name read from the line>;
switch (fruitName)
{
case "Apple":
{
newFruit = new Apple();
break;
}
case "Orange":
{
newFruit = new Orange();
break;
}
case "Banana":
{
newFruit = new Banana();
break;
}
default:
{
throw new ApplicationExce ption(fruitName + " is not
a recognized fruit type.");
break;
}
}

newFruit.setwei ght(<weigth read from file, converted to a float
value>);
theFruit.Add(ne wFruit);
}

HTH,
Nicole
"Jon Rea" <jr****@bris.ac .uk> wrote in message
news:WV******** ********@news-binary.blueyond er.co.uk...
I hav been looking for the last 2 hours on how to do this without much luck.
Im going to give a simplifed model of the problem i have.

I want a collection class that can holds a series or objects, for arguments sake, lets make these fruit :
apple
orange
bannana
in my application i have

public abstract class Fruit

{

float m_Weight = 0.0f;

public void setweight(float weight)

}

public class Apple : Fruit

{

}

public class Orange : Fruit

{

}

public class Bannana : Fruit

{

}
What i want to implement is a collection class that can hold a series of
items.

ArrayList theFruit = new ArrayList();

Now i want to open a file

pseudocode :

Openthefile(fru ity.txt)
{
foreach line in the file
{
find the correct object type
create that object type
add the data to it
add it to the collection class
}
}

Now the file will contain a list something like this, i.e. a random list of fruit.

Type, Weight
Bannana 1.03
Apple 2.12
Pear 4.23
Bannana 5.34
Bannana 1.22
Apple 3.33
How do i make the collection class contain objects of the correct type at
runtime ????

Many Thanks for anyones help
Jon Rea

Nov 15 '05 #3
And thereby allow potentially dangerous invocation of any validly named
object based on data coming from who knows where? At a bare minimum,
checking if the specified type is actually a Fruit subclass before creating
an instance might be a good idea. However, even that might not be
sufficient. For example, the data could specify the name of a class that
inherits from Fruit but is never meant to be instantiated based on the file
data. Such as class could be dangerous, or even just error out in
unexpected ways (e.g.: another abstract base class that inherits from
Fruit).

If one follows the usual "don't trust user data" rules, validating for
membership in the list of allowed class names is a much better approach. In
addition, this approach would allow for re-mapping of a name onto another
class if necessary (e.g.: "Apple" data is used to specify invocation of a
new FancyApple class).

Nicole
"Jon Skeet" <sk***@pobox.co m> wrote in message
news:MP******** *************** *@news.microsof t.com...
Jon Rea <jr****@bris.ac .uk> wrote:
I hav been looking for the last 2 hours on how to do this without much luck.
Im going to give a simplifed model of the problem i have.


<snip>

Assuming they all have the same properties, the way to do it is:

o Use Type.GetType to get the type listed in the file.
o Check that the type has actually been found (i.e. Type.GetType hasn't
returned null).
o Use Activator.Creat eInstance to create an instance of the type.
o Cast the returned reference to the base type (Fruit in your example)
o Call SetWeight etc with the rest of the data in the line.

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too

Nov 15 '05 #4
Nicole Calinoiu <ni*****@somewh ere.net> wrote:
And thereby allow potentially dangerous invocation of any validly named
object based on data coming from who knows where?
Well, if the type doesn't include the assembly name (which it won't if
it's taken from a comma-separated list as shown) then it can only come
from the executing assembly itself or mscorlib...
At a bare minimum,
checking if the specified type is actually a Fruit subclass before creating
an instance might be a good idea.
Sure. I was offering an outline, not bullet-proof production code.
However, even that might not be
sufficient. For example, the data could specify the name of a class that
inherits from Fruit but is never meant to be instantiated based on the file
data. Such as class could be dangerous, or even just error out in
unexpected ways (e.g.: another abstract base class that inherits from
Fruit).

If one follows the usual "don't trust user data" rules, validating for
membership in the list of allowed class names is a much better approach. In
addition, this approach would allow for re-mapping of a name onto another
class if necessary (e.g.: "Apple" data is used to specify invocation of a
new FancyApple class).


Yes. It really depends on exactly how this data was generated, the rest
of the application etc. There are times when you've got to trust user-
provided data (e.g. if the user could give their own fruit class, in
which case the OP would also need a way of loading the appropriate
assembly) and times where it's best not to. I was basically just
showing how to go about instantiating a type given only the name of the
type at runtime.

However, *if* all classes (and there could be many) provide an
identical constructor form, a simple map from name to type, followed by
the Activator.Creat eInstance call shown before could be neater (albeit
fractionally slower) than the direct instantiation way you showed.

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 15 '05 #5
"Jon Skeet" <sk***@pobox.co m> wrote in message
news:MP******** *************** *@news.microsof t.com...
Well, if the type doesn't include the assembly name (which it won't if
it's taken from a comma-separated list as shown)
Actually, it was space-delimited in the example, which doesn't preclude
specification of the assembly. Even comma-delimited could allow it if
individual data elements are wrapped in quotes.

then it can only come
from the executing assembly itself or mscorlib...
And there's nothing in mscorlib that one might not want to invoke like this?
At a bare minimum,
checking if the specified type is actually a Fruit subclass before creating an instance might be a good idea.


Sure. I was offering an outline, not bullet-proof production code.


I did realize that. <g> Unfortunately, I've seen (and subsequently had to
fix) quite a bit of production code that uses "nifty" tricks like this
without any consideration of the run-time consequences, and I worry a lot
more about what the potential beginner readers of this thread will do in
their code than what you might do in yours.

Yes. It really depends on exactly how this data was generated, the rest
of the application etc.
Not really. All you know is that it's in a file. Unless you're monitoring
the file for potential tampering, and the monitor never been "turned off",
and you're absolutely certain it's unhackable, you have no idea how the data
got into the file.

There are times when you've got to trust user-
provided data
As a special priviledge within an application, maybe. Otherwise, I'd have
to disagree.
(e.g. if the user could give their own fruit class, in
which case the OP would also need a way of loading the appropriate
assembly) and times where it's best not to.
For this kind of extensibility, it might be best to allow the programmer
"user" to extend a factory class in order to allow instantion of their
custom objects. Personally, I wouldn't want to be blamed for their security
holes. <g>

However, *if* all classes (and there could be many) provide an
identical constructor form, a simple map from name to type, followed by
the Activator.Creat eInstance call shown before could be neater (albeit
fractionally slower) than the direct instantiation way you showed.


I agree, but I would use the following form to both enforce the target type
restrictions and get around the constructor limitation:

switch (theClassName)
{
case "a":
case "b":
{
newObject = Activator.Creat eInstance(Type. GetType(theClas sName));
break;
}
case "c":
case "d":
{
newObject = Activator.Creat eInstance(Type. GetType(theClas sName),
<some args>);
break;
}
case "e":
{
newObject = Activator.Creat eInstance(Type. GetType(theClas sName),
<some other args>);
break;
}
...
default:
{
throw <a big, fat exception>;
break;
}
}
Nov 15 '05 #6
Nicole Calinoiu <ni*****@somewh ere.net> wrote:
"Jon Skeet" <sk***@pobox.co m> wrote in message
news:MP******** *************** *@news.microsof t.com...
Well, if the type doesn't include the assembly name (which it won't if
it's taken from a comma-separated list as shown)
Actually, it was space-delimited in the example, which doesn't preclude
specification of the assembly.


True, whoops.
Even comma-delimited could allow it if
individual data elements are wrapped in quotes.


Assuming the code coped with quotes, of course - which it may not need
to.
then it can only come
from the executing assembly itself or mscorlib...


And there's nothing in mscorlib that one might not want to invoke like this?


I never suggested that.

<snip>
Yes. It really depends on exactly how this data was generated, the rest
of the application etc.


Not really. All you know is that it's in a file. Unless you're monitoring
the file for potential tampering, and the monitor never been "turned off",
and you're absolutely certain it's unhackable, you have no idea how the data
got into the file.


Are you also going to check somehow that the assembly hasn't been
tampered with either?
There are times when you've got to trust user-
provided data


As a special priviledge within an application, maybe. Otherwise, I'd have
to disagree.


I guess we'll have to agree to disagree then.
(e.g. if the user could give their own fruit class, in
which case the OP would also need a way of loading the appropriate
assembly) and times where it's best not to.


For this kind of extensibility, it might be best to allow the programmer
"user" to extend a factory class in order to allow instantion of their
custom objects. Personally, I wouldn't want to be blamed for their security
holes. <g>


How do you then instantiate the factory class without running into the
same potential problem?
However, *if* all classes (and there could be many) provide an
identical constructor form, a simple map from name to type, followed by
the Activator.Creat eInstance call shown before could be neater (albeit
fractionally slower) than the direct instantiation way you showed.


I agree, but I would use the following form to both enforce the target type
restrictions and get around the constructor limitation:


<snip>

I think it really depends on stuff we don't know anything about: how
many types are involved, how many different sets of parameters are
involved, etc. I generally find a table lookup more maintainable, but I
certainly wouldn't like to say without more information.

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 15 '05 #7
"Jon Skeet" <sk***@pobox.co m> wrote in message
news:MP******** *************** *@news.microsof t.com...
And there's nothing in mscorlib that one might not want to invoke like this?

I never suggested that.
I didn't really mean to imply that you had. 'Twas meant to be a bit of
irony, but I guess that didn't really come through...

Not really. All you know is that it's in a file. Unless you're monitoring the file for potential tampering, and the monitor never been "turned off", and you're absolutely certain it's unhackable, you have no idea how the data got into the file.


Are you also going to check somehow that the assembly hasn't been
tampered with either?

Well, .NET does have some lovely mechanisms for doing just that will very
little work on the behalf of the developer. I'd be even more worried about
tampering with the tracking log than with the assembly itself. That said, I
would never implement this sort of mechanism. IMO, it's quite a bit less
work to apply the validation that is necessary if one doesn't trust the
data.

There are times when you've got to trust user-
provided data


As a special priviledge within an application, maybe. Otherwise, I'd have to disagree.


I guess we'll have to agree to disagree then.


Different perspectives, I'd guess. I've probably spent way too long working
on web apps with privacy implications, where even app, machine, and db
admins may not read or modify most of the data. All my users are
potentially nosey snoops, and script kiddies might even outnumber legitimate
users. A few years of that tends to make one a bit cynical about user
input...
For this kind of extensibility, it might be best to allow the programmer
"user" to extend a factory class in order to allow instantion of their
custom objects. Personally, I wouldn't want to be blamed for their security holes. <g>


How do you then instantiate the factory class without running into the
same potential problem?


CAS with custom permissions and evidence. For example, a developer edition
of the software could include a token used as evidence in granting
permissions to call the protected and public members of the base factory
class.

I think it really depends on stuff we don't know anything about: how
many types are involved, how many different sets of parameters are
involved, etc. I generally find a table lookup more maintainable, but I
certainly wouldn't like to say without more information.


I sort of like the lookup approach too for large parameter sets,
particularly if it's reasonable to use the prototype pattern, but only if
the class set is substantially smaller than the parameter set. I would hope
that I would wake up and see the forest for the fruit before a 100-headed
monster creeps up on me... <g>
Nov 15 '05 #8
Nicole Calinoiu <ni*****@somewh ere.net> wrote:

<snip>
Different perspectives, I'd guess. I've probably spent way too long working
on web apps with privacy implications, where even app, machine, and db
admins may not read or modify most of the data. All my users are
potentially nosey snoops, and script kiddies might even outnumber legitimate
users. A few years of that tends to make one a bit cynical about user
input...


For webapps, certainly - although there when you're talking about users
you're talking about people without access to the file system, so
whereas you don't trust input that comes over the wire, you may be able
to trust data which you yourself have previously written to disk.
How do you then instantiate the factory class without running into the
same potential problem?


CAS with custom permissions and evidence. For example, a developer edition
of the software could include a token used as evidence in granting
permissions to call the protected and public members of the base factory
class.


All that is fine when it's absolutely needed - but frankly in most
situations I think it's going to be over the top.
I think it really depends on stuff we don't know anything about: how
many types are involved, how many different sets of parameters are
involved, etc. I generally find a table lookup more maintainable, but I
certainly wouldn't like to say without more information.


I sort of like the lookup approach too for large parameter sets,
particularly if it's reasonable to use the prototype pattern, but only if
the class set is substantially smaller than the parameter set. I would hope
that I would wake up and see the forest for the fruit before a 100-headed
monster creeps up on me... <g>


Fair enough :)

--
Jon Skeet - <sk***@pobox.co m>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 15 '05 #9
"Jon Skeet" <sk***@pobox.co m> wrote in message
news:MP******** *************** *@news.microsof t.com...
Nicole Calinoiu <ni*****@somewh ere.net> wrote:
How do you then instantiate the factory class without running into the
same potential problem?


CAS with custom permissions and evidence. For example, a developer edition of the software could include a token used as evidence in granting
permissions to call the protected and public members of the base factory
class.


All that is fine when it's absolutely needed - but frankly in most
situations I think it's going to be over the top.


I most definitely agree. However, I do think that this particular situation
of instantiating objects based on their names is sufficiently dangerous that
adequate protection is necessary. My preference would be to validate the
externally sourced names against a strict inclusion list and prevent any
external use of the factory classes.

If external use is necessary (e.g.: because of an extensibility
requirement), there's probably some simpler mechanism for ensuring that use
from external code is reasonably safe. I haven't yet encountered a need to
expose such potentially dangerous code for extensibility in my own work, so
I haven't really dug deep into the potential ramifications of just allowing
OOP "tricks" and standard CAS to handle the issue.
Nov 15 '05 #10

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

0
1210
by: windandwaves | last post by:
Hi Gurus I was wondering if you know of any good php class for editing mysql data from a users point of view. Kind of like PHP My Admin but then really simple and efficient. I have a look at www.phpclasses.org, but have not been able to find anything. Thank you
4
1581
by: Ben McLaurin | last post by:
When oopeening a form based of a table I need to run a function to do some calculations. Which form event do I need to use that will automatcally run when the form is opened but all the data from the record is available. Tried a few that seems to make sense but I believe I am missing something obvious.
2
1547
by: Jim | last post by:
I'm writing an Invoicing Windows app but I'm writing it to make the code as easy to maintain as possible. Basically, to get any records from my DB, I use two classes: one that sets up the SQL statement, and another that makes the connection (plus the class that contains the windows form). Now, is this the best way to divide my tasks? And by...
2
2886
by: Alvaro E. Gonzalez V. | last post by:
Hi; I'm building a control that has a DataTable's property type. The control contains treeview which is populated in foreach crossing rows of the DataTable established in the property. I require a mechanism so that when they change the loaded data of the DataTable these are reflected in treeview. Somebody can offer information to...
13
4520
by: Fei Liu | last post by:
Hi Group, I've got a problem I couldn't find a good solution. I am working with scientific data files in netCDF format. One of the properties of netCDF data is that the actual type of data is only known at run time. Therefore a lot of template based trick isn't too useful. Considering datafile float x(3) 3.5, 2.5, 8.9 double y(3)...
4
2428
by: gazelle04 | last post by:
I have reports based on data from the combo box. Everytime I want to print I have to select from the combo box. Now I want to print them all without having to select each time from the combo box. Can somebody send me a sample code for iterating in the combo box so that I can have a routine to print my all my reports in just one click.
6
3497
by: Hubert Fritz | last post by:
Hello, I fear I want to have something which is not possible in C++. How is it possible to define a base class so that the derived class is forced to contain a static member variable, which can be used by static member functions of the base class? Something like virtual static XClass* pXClass; /* pXClass shall be pure virtual, so not...
8
1752
by: Johs | last post by:
I see a lot of different conventions on the net when it comes to making a class. Currently I make a class in a single .cc file like: #include <string> #include <iostream> using namespace std; class List { private: string name;
1
1626
by: inamul | last post by:
I want to select CheckBox based on data retrieved from mysql database table. Could anyone show me the simple way of doing it. Data store in table under colum "sectionOfInterest" is shown below ------------------------------------------------------------------------ "Commercial Security Middle East, Homeland Security and Policing Middle...
0
7852
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language...
0
8216
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. ...
0
8349
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that...
0
8221
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the...
0
6629
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then...
0
3845
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in...
0
3882
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
1
2364
by: 6302768590 | last post by:
Hai team i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system
1
1455
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.

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.