|
-
Dec 3rd, 2008, 06:47 PM
#1
Thread Starter
Fanatic Member
[RESOLVED] sub returning diffrent types
Hey all.
I two subs that are almost exactly identical that return two different types of control
I would use the sub something like
textbox1.text = stringtoMatchtype1("match1").chatter;
where chatter is a property of matchtype1(and 2)
I could just return a control but then i couldnt access the propertys and methods of that contorl.
any ideas to point me down a better path?
c# Code:
private MatchType1 StringToMatchType1(string name)
{
foreach (TabPage tp in tabControl1.Controls)
{
foreach (Control c in tp.Controls)
{
if (c is MatchType1)
{
if (c.Name == name)
{
return (MatchType1)c;
}
}
}
}
throw new Exception("Matchtype1 not found" + name);
}
private MatchType2 StringToMatchType2(string name)
{
foreach (TabPage tp in tabControl1.Controls)
{
foreach (Control c in tp.Controls)
{
if (c is MatchType2)
{
if (c.Name == name)
{
return (MatchType2)c;
}
}
}
}
throw new Exception("Matchtype2 not found" + name);
}
-
Dec 3rd, 2008, 07:10 PM
#2
Hyperactive Member
Re: sub returning diffrent types
you could just make one method that returns the Control as it is and then cast it since you already know what the type is.
-
Dec 3rd, 2008, 08:07 PM
#3
Thread Starter
Fanatic Member
Re: sub returning diffrent types
i could but it seems like a lot extra repeat code
-
Dec 3rd, 2008, 09:15 PM
#4
Hyperactive Member
Re: sub returning diffrent types
i was proposing using one method and just searching by name. You could also use a generic method if you are using .net 3.5
vb.net Code:
private T FindControl<T>(string name)
{
foreach (Control c in this.Controls)
{
if (c.Name == name && c is T)
{
Type retType = typeof(T);
return (T)Convert.ChangeType(c, retType);
}
}
return default(T);
}
then if you're looking for a button do the following:
Button b = FindControl<Button>("YourButtonName");
You could also change this to a nongeneric method and return an object. Then cast appropriately. I don't think it's possible anyway to have a control of the same name so you shouldn't have trouble.
-
Dec 3rd, 2008, 10:05 PM
#5
Frenzied Member
Re: sub returning diffrent types
You could make MatchType an interface and then have MatchType1/MatchType2 inherit from it.
-
Dec 3rd, 2008, 10:18 PM
#6
Re: sub returning diffrent types
There's no such thing as a "sub" in C#. That's a VB thing. In VB a Sub is a method that doesn't return a value and a Function is a method that does return a value. In C# all methods are functions. The C# equivalent of a VB Sub is a void function. That said, both your functions DO return something so they wouldn't be Subs in VB even.
wy25 has the right of it, except that this is neater:
CSharp Code:
private T FindControl<T>(string name) where T:Control { foreach (Control ctl in this.Controls) { if (ctl is T && ctl.Name == name) { return (T)ctl; } } return null; }
You constrain T to inherit Control and then the compiler allows you to cast as T inside the method. You can also return null explicitly instead of using default because you know that any type that inherits Control must be a reference type.
-
Dec 4th, 2008, 03:23 PM
#7
Thread Starter
Fanatic Member
Re: sub returning diffrent types
how is that any diffrent than just returning the type of control.
i would still have to cast it as the type im expecting but now i just would do it where it was called rather than in the method itself
i'm trying to avoid this because it leaves little nuggets of repeat code all over the place.
-
Dec 4th, 2008, 05:16 PM
#8
Re: sub returning diffrent types
what? You wouldn't need to cast it... it would already be done as part of <T> .... you specify the type you are looking for on the way in.... the object that comes out (if not NULL) will be of that type.
And what "nuggets of repeat code" are you going on about?
-tg
-
Dec 4th, 2008, 05:37 PM
#9
Re: sub returning diffrent types
This work for you?
Code:
private MatchType1 FindControl(string value)
{
return this.Controls.OfType<MatchType1>().Where(c => c.chatter == value).FirstOrDefault();
}
-
Dec 4th, 2008, 06:26 PM
#10
Re: sub returning diffrent types
 Originally Posted by syntaxeater
This work for you?
Code:
private MatchType1 FindControl(string value)
{
return this.Controls.OfType<MatchType1>().Where(c => c.chatter == value).FirstOrDefault();
}
That's a a nice use of LINQ that leads to some concise code. To combine the generic method suggested by by wy125, the constraint suggested by myself and the LINQ suggested by syntaxeater:
CSharp Code:
public T FindControl<T>(string name) where T : Control
{
return this.Controls.OfType<T>().Where(c => c.Name == name).FirstOrDefault();
}
Now you can use that method to return a control of any specific type with a specific name.
As tg said, the whole point of generics is to be able to use the same code for many different types. This method returns a reference of type T where YOU specify what T is when you call the method. If you call the method like this:
CSharp Code:
this.FindControl<MatchType1>("something");
then the method will return a reference of type MatchType1. If you call it like this:
CSharp Code:
this.FindControl<MatchType2>("something");
then it will return a reference of type MatchType2. If you call it like this:
CSharp Code:
this.FindControl<Button>("something");
then it will return a reference of type Button.
If you use a List<T> do you have to cast the items as you get them? Of course not. You specify what T is when you create the List and then every item you get from the List is that type. There's no need to cast. Generic methods are the same. You fix T when you call the method and then every use of T in the method becomes that type. In this case the return type of the method is T, so if you fix T to be Button then the return type of the method becomes Button. Etc.
-
Dec 4th, 2008, 06:54 PM
#11
Hyperactive Member
Re: sub returning diffrent types
that's pretty cool guys. I've learned something new...
-
Dec 4th, 2008, 09:10 PM
#12
Re: sub returning diffrent types
I should actually point out an error in my earlier terminology that many people make. The code that syntaxeater provided earlier and I modified doesn't actually use LINQ per se. It uses extension methods and lambda expressions directly. They are both language features that were added to support LINQ but their use is not limited to LINQ exclusively. There's no actual LINQ query in that code so it's not actually LINQ. It's still pretty cool code, but an actual LINQ implementation would have to contain an actual query, with a 'where' clause rather than a call to the Where method. Of course, such a query would be implemented in much the same way as the code provided.
-
Dec 4th, 2008, 10:44 PM
#13
Re: sub returning diffrent types
Here's the equivalent using an actual LINQ query:
CSharp Code:
public T FindControl<T>(string name) where T : Control { return (from t in this.Controls.OfType<T>() where t.Name == name select t).FirstOrDefault(); }
As far as I'm aware the OfType and FirstOrDefault calls can't be folded into the query syntax in any way.
-
Dec 5th, 2008, 03:29 PM
#14
Thread Starter
Fanatic Member
Re: sub returning diffrent types
 Originally Posted by jmcilhinney
I should actually point out an error in my earlier terminology that many people make. The code that syntaxeater provided earlier and I modified doesn't actually use LINQ per se. It uses extension methods and lambda expressions directly. They are both language features that were added to support LINQ but their use is not limited to LINQ exclusively. There's no actual LINQ query in that code so it's not actually LINQ. It's still pretty cool code, but an actual LINQ implementation would have to contain an actual query, with a 'where' clause rather than a call to the Where method. Of course, such a query would be implemented in much the same way as the code provided.
i see now
I will try this out and let you know
Thanks
-
Dec 8th, 2008, 06:07 PM
#15
Re: sub returning diffrent types
 Originally Posted by jmcilhinney
Here's the equivalent using an actual LINQ query:
CSharp Code:
public T FindControl<T>(string name) where T : Control
{
return (from t in this.Controls.OfType<T>()
where t.Name == name
select t).FirstOrDefault();
}
As far as I'm aware the OfType and FirstOrDefault calls can't be folded into the query syntax in any way.
OfType - There is a way, but not one more concise than what has been previously suggested:
Code:
public T FindControl<T>(string name) where T : Control
{
return (T)(from Control t in this.Controls
where t.GetType() == typeof(T) && t.Name == name
select t).FirstOrDefault();
}
However, using Extension OfType is by far a nicer means (in my opinion).
FirstOrDefault - no, you can't. The query will not execute until one of the Linq.Enumerable members that produces a result has been called. As far as I am aware, there's no way for it to change the return type based on an anticipated number of results from the expression alone.
-
Dec 8th, 2008, 06:39 PM
#16
Re: sub returning diffrent types
 Originally Posted by syntaxeater
OfType - There is a way, but not one more concise than what has been previously suggested:
Code:
public T FindControl<T>(string name) where T : Control
{
return (T)(from Control t in this.Controls
where t.GetType() == typeof(T) && t.Name == name
select t).FirstOrDefault();
}
However, using Extension OfType is by far a nicer means (in my opinion).
FirstOrDefault - no, you can't. The query will not execute until one of the Linq.Enumerable members that produces a result has been called. As far as I am aware, there's no way for it to change the return type based on an anticipated number of results from the expression alone.
I was thinking of a specifically LINQ way to replace the OfType call, which there isn't. Certainly there's nothing wrong with testing the type in the 'where' clause but it does then require casting the result before returning, as you've done. If I was going to test the type in the 'where' clause I'd do it with the 'is' operator:
CSharp Code:
public T FindControl<T>(string name) where T : Control
{
return (T)(from Control t in this.Controls
where t is T && t.Name == name
select t).FirstOrDefault();
}
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|