|
The cost of that type of conversion (regardless of whether it's implicit of explicit) will be trivial if you're actually doing anything with the result. It's a bit faster than casting to an abstract base class.
From a quick test: you can do a million of calls to your SomeMethod in 15 to 25 miliseconds.
|
|
|
|
|
Hi Bill,
BillWoodruff wrote: SomeOtherClass.SomeMethod(this, "some string");
there is no cost at all, the compiler checks your code and sees your this indeed conforms to the expected parameter type (TheInterface iFace ), so all that happens at run-time is a pointer gets passed, no run-time checking is involved.
It would be exactly the same as passing a TextBox to a method that accepts a Control ; the compiler would see how TextBox implements Control , so all is well and free.
|
|
|
|
|
I agree with Luc.
There is no "casting", no "conversion". No bad smell.
|
|
|
|
|
Hi Bill,
I know where you are coming from with this having being involved in some discussion on the same thread.
I agree with the others, there is no cost involved - to answer your question.
Another/different question is should you pass an object (disguised as an interface or not) to another for simplicity of communication between the objects?
Personally, I think not. An interface is a slight improvement to passing a concrete object, but I instinctively feel the 'secondary' object should be raising an event that the 'primary' object can choose to subscribe to or not depending on whatever logic is appropriate, and if subscribed - react or not. If the 'primary' needs to communicate with the 'secondary' then it should retain a reference to it - whether that is as an interface or not is irrelevant.
In other words, I see no particular improvement or benefit between these two, I disapprove of them both equally!
public partial class FormPrimary : Form
{
public FormPrimary()
{
InitializeComponent();
}
public void SetText(string text)
{
Text = text;
}
}
public partial class FormSecondary : Form
{
private FormPrimary primary;
public FormSecondary()
: this(null)
{ }
public FormSecondary(FormPrimary primary)
{
InitializeComponent();
this.primary = primary;
}
private void SetPrimaryText(string text)
{
if (primary != null)
{
primary.SetText(text);
}
}
}
public interface IStuff
{
void SetText(string text);
}
public partial class FormPrimary : Form, IStuff
{
public FormPrimary()
{
InitializeComponent();
}
public void SetText(string text)
{
Text = text;
}
}
public partial class FormSecondary : Form
{
private IStuff primary;
public FormSecondary()
: this(null)
{ }
public FormSecondary(IStuff primary)
{
InitializeComponent();
this.primary = primary;
}
private void SetPrimaryText(string text)
{
if (primary != null)
{
primary.SetText(text);
}
}
}
Just my initial feelings and I am interested to see how this turns out!
|
|
|
|
|
Hi Dave, A most interesting, thoughtful, and much appreciated reply => +5
I have gone through "phases," it seems, in my very humble[1] evolution in programming in C#.
For a while, I seemed focused on 'passing around everything' by raising events, and transmitting data through custom EventArgs.
Then, in my head, I began to feel that there were two "modes" to consider here: one mode was "access:" at times Class/Form/Object A needs to have access to some Field/Property/Data in Class/Form/Object B ... and the principle of "separation of concerns" is the reason why Object A is not designed to be "intimate" with Object B (such as by sharing an Interface, or Inheritance).
And, the other mode, was "raising Events.
I began to think that in terms of this hypothetical "access mode," that the right thing to do was to expose, somehow, in Object B, what Object A "needed to know."
At that point I went into a "phase" where "injection" seemed the right thing to do: plug a reference to the instance of Object B into Object A, and then Object A can "help itself" to everything publicly exposed in Object B.
Then I came to feel that injection was (at least in the broad way I was using it) over-kill, and kind of a violation of separation of concerns. The old security buzz-word "need-to-know" seemed relevant to me here.
Then I entered a phase where I focused on creating static "Manager" classes through which interaction, and exchange of information between Objects/Classes/Forms was handled, in some cases assigning Events to Objects inside the static Manager class, at times just publishing methods in the static Manager class that any Object could invoke, passing in whatever.
And I still like this "static class" Manager idea in a scenario where you may have a whole bunch of run-time created objects of the same type active. For example, a "sticky note" application where you want to modify the content of some, or all, "stickies," based on some action in one particular "sticky."
And, finally, I came to the current phase, which I might call "parsimonious accessibility:" if there's one something in Object B that Object A needs access at times to: then, in Object B, define a Public Property that exposes what Object A needs to know.
Meanwhile, and this may not be a good thing, I seem to have come to rely on Events much less than ever: raising a custom event only when its directly related to asynchronous user behavior at run-time.
So, right now, the use of Interfaces, as a way to "limit exposure" between Objects is kind of the "new dance craze" for me, since I seem to have under-estimated what interfaces can do. And such interesting possibilities as explicit rather than implicit implementation of interfaces tantalize me[^].
My long-range goal here is simple: to have the depth of knowledge to approach solutions to real-world problems involving both algorithms, and asynchronous UI design, and OO application architecture, with a broad "palette" of techniques for inter- and infra- object communication/access tempered by awareness of the usefulness, efficiency, relevance, and cost/benefits of the varying. In other words, to have some sense of "best practice."
My mind is wide-open, and I'm ready to go "cold turkey" to withdraw from addiction(s) to any "phases."
best, Bill
[1] Picking out any one chapter, and reading, in Jon Skeet's "C# in Action" absolutely tops-up my "humility buffer" !
"Last year I went fishing with Salvador Dali. He was using a dotted
line. He caught every other fish." Steven Wright
|
|
|
|
|
+5 for the open mind - never a bad thing
I hope this attracts the attention of some of the forum die hards regulars as I would really value their opinions too in this OO philosophy debate. SAK has decided this is the mechanism for him which is great, but he is touting it around the CP world (and getting good votes as it's a simple methodology to implement and use) as the most 'robust' etc solution to inter object communication and one they should all use, but I am yet to be convinced
|
|
|
|
|
The issue you are describing is one of the classic issues surrounding IoC, and whether or not to use constructor injection to manage dependencies. At first, this seems to be an attractive option because it is a quick and easy way to add dependencies between objects. What BillWoodruff is effectively describing is the foundation of an IoC solution whereby you use interfaces to allow you to decouple the implementation from the consumption of the functionality. This is a classic situation especially when combined with Test Driven Development whereby you can easily inject mock functionality.
So, how about constructor injection? Why wouldn't you want to use it? Well, in the sample that Dave shows here, there's nothing inherently wrong with passing the interface into the constructor. What happens, though, when you want to add another interface that your class needs to consume? Well if you are using constructor injection, you need to either add another constructor or you need to modify the existing one and all the places that it's called in the code. The more complex a system becomes, the bigger this problem will get.
Now, one way to tackle this is to use property injection instead. In other words, your class adds properties that have the appropriate type and anytime the functionality is needed, the property is used. This is a simple and effective way to get around the scenario described above. But does this solve the question posed by Dave? Well, yes and no.
If you simply need a means to communicate between one object and another, then passing a concrete instance or an interface around is sheer overkill. Whenever I see somebody recommend this, it makes the very core of me want to reach out and slap them repeatedly. So, why do I think this? Well, have a think about what would happen if you started to play around with the values of that object inside your consuming object. Now think about what happens if you start to do this inside threaded code. Now think about the fact that all you really needed to do was let the original object know that it needs to update the text in the UI thread. In this type of situation, the much simpler and safer method is to simply have an event that is subscribed to, and let that raise the changes.
Anyhoo - those are just some rambling musings designed to get people thinking. Hope it helps.
|
|
|
|
|
Pete O'Hanlon wrote: rambling musings designed to get people thinking
It's certainly done that! Thanks for the input Pete, I'm sure Bill will muse too
|
|
|
|
|
This is one of those subjective, grey area questions. There are times when direct linkage is appropriate (generally for things within the same library or application) – for example I think it makes sense for a collision hull to have a direct reference to its host object, as well as vice versa, because it's tightly bound to it (a hull always has a parent object and an object can always have a hull, though some may choose to have a null one). When it crosses library boundaries, you often want to have the linkage in one direction (an 'upward' link in normal layer terminology) to be an interface in order to keep the layers in the right order. And sometimes you want the looser coupling of simply exposing events and allowing someone to hook onto them if they wish.
You can go a step further and have a single central event source which everyone can post messages into and retrieve them out of, as the Unity framework does (IEventAggregator), so you don't have to have a reference to something to hook onto its events. But I find that to be confusing, particularly trying to work out execution paths that have been done like this in other people's code – once you introduce global components like that, everything can depend on it and modularisation is broken.
I only tend to use events for unpredictable, well, events – things caused by user input or other external sources (network, file etc), or asynchronous execution (threads, BackgroundWorkers, etc).
|
|
|
|
|
Where an object ALWAYS has a host/parent and should not exist without it AND requires knowledge of it directly, then the coupling is fine IMO, although often still not required or the best way.
If there is any possibilty that it could now, or at some point in future, be used without a host then there should be no direct coupling.
Of course, if it can have several different hosts then coupling to a common base or interface may be a reasonable solution.
BobJanova wrote: a single central event source
Not keen on this though I can see how this can be useful.
Thanks for the post, all thoughts and variations in this debate are welcomed
|
|
|
|
|
Hi Bill,
To start with, let me note that the implicit cast from an instance of implementing class to the interface reference is not always possible. Consider this:
public class SimpleClass : TheInterface {
string TheInterface.iText { get; set; }
void Test() {
TheInterface intrf = this;
intrf.iText = "will work";
((TheInterface)this).iText = "will work";
}
}
Please pay attention: I switched to explicit implementation of interface member TheInterface.iText and eliminated public to make this experiment pure and possible. If I worked with implicit implementation and public , the result would be difficult (all forms would work), just because there are two different "views" of iText : in is a member of TheInterface , another one — a (public) member of SimpleClass . Physically this is the same but those are different things from the access standpoint. With explicit implementation, actual assignment would be done with the member of SimpleClass . Of course, the same story goes with regular methods.
[EDIT]
I would recommend to prefer explicit interface implementation over implicit one. It has additional benefits in many cases. (One of them — a possibility to have more than one indexed ("this") properties (of different signatures).)
[END EDIT]
In a next step, I'll try to convince you that a cast to interface reference may be not so trivial. To understand that, let's consider the weak form of multiple inheritance:
internal interface IFirst {
string A { get; set; }
int B { get; set; }
}
internal interface ISecond {
string C { get; set; }
double D { get; set; }
}
internal class Implementation : IFirst, ISecond {
string IFirst.A { get; set; }
int IFirst.B { get; set; }
string ISecond.C { get; set; }
double ISecond.D { get; set; }
}
How this can be implemented when you cast the instance of Implementation to first IFirst and ISecond ? The "physical" references should be different. I don't know exact memory layout of the instance, but we can imagine it based on some C++ experience:
[Reference to TypeOf(Implementation)]
...
other methods
[Reference to TypeOf(IFirst)] -- reference to the code of IFirst points here
...
IFirst.A.Get
IFirst.A.Set
IFirst.B.Get
IFirst.B.Set
[Reference to TypeOf(ISecond)] -- reference to the code of ISecond points here
...
ISecond.C.Get
ISecond.C.Set
ISecond.D.Get
ISecond.D.Set
...
The above diagram is similar to the Virtual Method Table. The reference to any object is a double "pointer": 1) to the area in memory where the instance data starts; 2) to the area in memory where the addresses of the methods start, 3) everything else.
The "pointer" (1) is different for different instances of the class, and the "pointer" (2) is the same per type, but it should be different if the implementing class is the same but it is cast to one or another interface.
"Pointer" is taken in quote to show its difference with .NET "references" which allow objects to be relocated in a way transparent for applications.
This is actually my fantasy, but it's based on my study of memory layout for C++ and Delphi implementing COM interfaces. Otherwise, how could it work? All method addresses should be dispatched during run time; and dispatching mechanism should have good performance, so all called via dynamic dispatch should simply take the table of methods (it could be different from mine) and operate the offset relative to the start of interface, because only the interface reference is provided at the point of the call.
So, I think that the cast to different interfaces could involve the reference "shift" and associated cost. This cost could be so small though so it might be not detectable. I'm not 100% sure those as the dispatching mechanism could be slightly different from that of COM or anything else I know. It would be interesting to study it in detail.
Thank you.
—SASergey A Kryukov
modified 8-Nov-11 22:40pm.
|
|
|
|
|
Hey Omar Gameel,
I came across your implementation in C# on http://www.codeproject.com/KB/recipes/AprioriAlgorithm.aspx
I need your help, I need an improvised version of Apriori Algorithm that is more efficient and scalable for my college. Can you please help me with it?
Thanks,
crce
|
|
|
|
|
You should probably reply to that article, the author may not find your post here.
|
|
|
|
|
Use the comment box at the bottom of the article.
This will notify Omar directly, he will then be able to help you.
------------------------------------
I will never again mention that I was the poster of the One Millionth Lounge Post, nor that it was complete drivel. Dalek Dave
CCC Link[ ^]
Trolls[ ^]
|
|
|
|
|
I have dynamically created a datagridview control with a DataGridViewCheckBoxColumn. The problem I have is that when I click on a checkbox cell, it does not set the check mark. I would like to know what I need to know in order to check and uncheck a checkbox when it is clicked. Thanks in advance.
|
|
|
|
|
There is no obvious reason for this to be the case.
Could you show your code.
If we can see any problems it can be spotted easier.
------------------------------------
I will never again mention that I was the poster of the One Millionth Lounge Post, nor that it was complete drivel. Dalek Dave
CCC Link[ ^]
Trolls[ ^]
|
|
|
|
|
I've seen that problem before, but I don't specifically remember how I solved it. I do recall that the problem was due to some properties that default one way in the IDE, but when you create the check box programmatically you have to set the parameters yourself. My suggestion is to use the debugger and check all the properties once the control is created and find out which one or ones are making the check box cell inactive.
CQ de W5ALT
Walt Fair, Jr., P. E.
Comport Computing
Specializing in Technical Engineering Software
|
|
|
|
|
Can you show your code for clarification?
|
|
|
|
|
hi everyone,am looking for a source code which can read an object 2D OR 3D designed by Autocad with C#. plz help me.
|
|
|
|
|
Try this[^].
Unrequited desire is character building. OriginalGriff
I'm sitting here giving you a standing ovation - Len Goodman
|
|
|
|
|
Good find!
------------------------------------
I will never again mention that I was the poster of the One Millionth Lounge Post, nor that it was complete drivel. Dalek Dave
CCC Link[ ^]
Trolls[ ^]
|
|
|
|
|
The difficult bit was figuring out which keywords to put into Google. Eventually after much trial and error I stumbled across "Autocad C#" ...
Unrequited desire is character building. OriginalGriff
I'm sitting here giving you a standing ovation - Len Goodman
|
|
|
|
|
Nah. Unless it is "help please", the first thing to do is paste the OP's subject line into the Google search box. Really easy.[^]
|
|
|
|
|
Er, I was being facetious Luc.
Unrequited desire is character building. OriginalGriff
I'm sitting here giving you a standing ovation - Len Goodman
|
|
|
|
|
Really?
|
|
|
|
|