.NET Forum / Languages / C# / October 2007
Creating a reference to an object
|
|
Thread rating:  |
mark.norgate@gmail.com - 27 Sep 2007 18:51 GMT Hello
I want to create a reference to an object, so that changes to the referenced object are reflected in the other object. Like this:
object o = 123; object p = o;
o = 456;
System.Console.WriteLine("o = {0}", o); System.Console.WriteLine("p = {0}", p);
456 123
I would like the output to be
456 456
How do I do this?
Mark
Peter Duniho - 27 Sep 2007 19:16 GMT > Hello > [quoted text clipped - 18 lines] > > How do I do this? You need to use a reference type rather than a value type.
In the code you posted, you start with a value type ("123", which is type "int"). You can assign it to a variable of type "object", but only because the C# compiler boxes it for you, creating a reference instance from the value instance. When you assign a new value type ("456", again an "int"), that value instance is again boxed; the reference created replaces the reference held by variable "o", rather than replacing the boxed value "o" referenced.
In other words, only the variable "o" is modified, rather than what "o" refers to.
If I recall, C# doesn't allow you to overload the = operator. So there's no way to write the code literally as you've done here. = will always _replace_ the contents of the variable you're assigning to, whether the variable holds a reference or a value.
But you can certainly accomplish the more general goal you stated: "to create a reference to an object, so that changes to the referenced object are reflected in the other object".
To do that, however, you need to have a mutable reference type and you need to modify an existing instance of that type. Any place where that instance is referenced will then see those modifications. For example:
class MyMutable { int _num;
public MyMutable(int num) { _num = num; }
public int Value { get { return _num; } set { _num = value; } } }
void Main() { MyMutable o = new MyMutable(123); MyMutable p = o;
o.Value = 456;
Console.WriteLine("o.Value = {0}", o.Value); Console.WriteLine("p.Value = {0}", p.Value); }
That will output:
o.Value = 456 p.Value = 456
Pete
mark.norgate@gmail.com - 27 Sep 2007 20:03 GMT Thanks for that Pete. It's clear now.
Mark
raylopez99 - 27 Sep 2007 23:50 GMT On Sep 27, 11:16 am, Peter Duniho <NpOeStPe...@NnOwSlPiAnMk.com> wrote: [Garbage deleted - just kidding]
This is not the last word however...see below. Essentially Pete's example is somewhat trivial, since p=o (identically) and other than as a placeholder in a loop, most programs need another copy of p. Below is an example using a shallow clone, with "p2" being a clone of p (which is identical with o). You might also consider a deep clone if your class inhereits other classes and is complex, since a shallow clone references the same objects as the orginal object, which will result in your clone being deleted if the original object gets deleted.
RL
//////////////////////// using System; using System.Collections.Generic; using System.Text;
namespace mutable { class Program { static void Main(string[] args) { MyMutable o = new MyMutable(123); MyMutable p = o; //MyMutable p2 = (MyMutable)p.Clone(); //gives 123 if placed here
o.Value = 456; MyMutable p2 = (MyMutable)p.Clone(); //gives 456 when placed here
Console.WriteLine("o.Value = {0}", o.Value); Console.WriteLine("o.hash is {0}", o.GetHashCode()); Console.WriteLine("p.Value = {0}", p.Value); Console.WriteLine("p.hash is {0}", p.GetHashCode()); //as can be seen when you run this code, p is the very same object as o Console.WriteLine("p2.Value = {0}", p2.Value); Console.WriteLine("p2.hash is {0}", p2.GetHashCode()); // as can be seen p2 is a different object than p (and o)
} } }
/* // output of above o.Value = 456 o.hash is 58225482 p.Value = 456 p.hash is 58225482 p2.Value = 456 p2.hash is 54267293 Press any key to continue . . .
*/ ////////////////////////////////////////////////////////
using System; using System.Collections; using System.Collections.Generic; using System.Text;
namespace mutable { class MyMutable : ICloneable { int _num;
public MyMutable(int num) { _num = num; }
public int Value { get { return _num; } set { _num = value; } } public object Clone() { return (this.MemberwiseClone()); //shallow clone } }
} //////////////
Peter Duniho - 28 Sep 2007 00:07 GMT > On Sep 27, 11:16 am, Peter Duniho <NpOeStPe...@NnOwSlPiAnMk.com> > wrote: > [Garbage deleted - just kidding] > > This is not the last word however...see below. Essentially Pete's > example is somewhat trivial, since p=o (identically) Um, that is the entire point. Only when ReferenceEquals() returns true for the two variables is this thread even relevant.
You may find it "trivial", but any other situation is outside the scope of the question. You are simply unnecessarily complicating the discussion thread.
Pete
Bill Butler - 28 Sep 2007 00:27 GMT > On Sep 27, 11:16 am, Peter Duniho <NpOeStPe...@NnOwSlPiAnMk.com> > wrote: [quoted text clipped - 3 lines] > example is somewhat trivial, since p=o (identically) and other than as > a placeholder in a loop, most programs need another copy of p. <snip>
I would disagree with the assertion that "most programs need another copy of p". I can't remember the last time I needed a Clone in my programs. Obviously there are certain situations that require a distinct copy, but honestly, I have not come across one in ages. Perhaps we are working in different problem domains.
Bill
Peter Duniho - 28 Sep 2007 00:37 GMT > I would disagree with the assertion that "most programs need another > copy of p". > I can't remember the last time I needed a Clone in my programs. In fact, if the OP were to use cloning to duplicate the original instance, he would not even get the behavior he's looking for.
> Obviously there are certain situations that require a distinct copy, but > honestly, I have not come across one in ages. Perhaps we are working in > different problem domains. Cloning does come up. But I completely agree; it is much less common that situations in which the original instance is sufficient (and in many cases, desirable).
I would be willing to bet that in .NET the single-most-common example of replicating in some fashion an instance of a reference type is the use of strings, and in that case you NEVER want a clone. I'd say that alone is the counter-example to the assertion you and I both disagree with. :)
Pete
raylopez99 - 28 Sep 2007 10:10 GMT > > wrote: > > [Garbage deleted - just kidding] [quoted text clipped - 13 lines] > > Bill I think Clone is just shorthand for what is known as a "copy constructor" in C++. Usually, in managed languages you "pass the pointer" (C++) or "pass the reference" (C#), so indeed clone is not often used, but it's used more often than you might think. That's because everytime you use "new", and other lines of code, essentially you are cloning--what is known as using the copy contructor in C++. The only advantage in C# using :ICloneable is that the base class :ICloneable makes replicating a duplicate class (a clone) much easier--no need to instantiate every composite object in such a class, to duplicate every member variable in it and set it to a value, etc, using 'new', etc, 'by hand'. Instead, you just pick either a deep or shallow clone and :ICloneable does everything for you, behind the scenes.
I hope I didn't needlessly complicate this thread...
RL
Bill Butler - 28 Sep 2007 13:07 GMT >> "raylopez99" <raylope...@yahoo.com> wrote in message <snip>
>> I would disagree with the assertion that "most programs need another >> copy of p". [quoted text clipped - 13 lines] > because everytime you use "new", and other lines of code, essentially > you are cloning--what is known as using the copy contructor in C++. <snip>
I don't understand that last bit at all. What do you mean by "everytime you use 'new', and other lines of code, essentially you are cloning"
That makes no sense to me. When I use new it has nothing to do with cloning.
Foo foo = new Foo(params);
There is no cloning involved here. I am creating a new instance of Foo. I didn't clone another instance of Foo to create it.
Can you clarify your point?
Bill
Jon Skeet [C# MVP] - 28 Sep 2007 15:03 GMT > That's because everytime you use "new", and other lines of code, essentially > you are cloning--what is known as using the copy contructor in C++. No. Using "new" creates a new object - that's all. There's absolutely *no* requirement that that new object be based on an existing one.
Jon
raylopez99 - 29 Sep 2007 22:12 GMT > > That's because everytime you use "new", and other lines of code, essentially > > you are cloning--what is known as using the copy contructor in C++. [quoted text clipped - 3 lines] > > Jon Thanks Jon for that narrow interpretation, but it's a bit off topic. Reread the words "and other lines of code" in the OP.
Thanks again, I apprecate your good work along with the other posters here.
Ray Lopez [C# MVP]
Jon Skeet [C# MVP] - 30 Sep 2007 18:19 GMT > > > That's because everytime you use "new", and other lines of code, essentially > > > you are cloning--what is known as using the copy contructor in C++. > > > > No. Using "new" creates a new object - that's all. There's absolutely > > *no* requirement that that new object be based on an existing one.
> Thanks Jon for that narrow interpretation, but it's a bit off topic. > Reread the words "and other lines of code" in the OP. > > Thanks again, I apprecate your good work along with the other posters > here. Your meaning was *extremely* unclear, which is why so many people misunderstood you.
 Signature Jon Skeet - <skeet@pobox.com> http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet If replying to the group, please do not mail me too
Peter Duniho - 28 Sep 2007 17:52 GMT > I think Clone is just shorthand for what is known as a "copy > constructor" in C++. Well, it's not. Clone is a specific reference to the Clone() method found in the ICloneable interface.
> Usually, in managed languages you "pass the > pointer" (C++) or "pass the reference" (C#), so indeed clone is not > often used, but it's used more often than you might think. No, it's not. It's used as infrequently as we think.
> That's > because everytime you use "new", and other lines of code, essentially > you are cloning No, you're not. "new" creates a new instance of an object. Cloning an object requires the use of "new", but "new" very much does not imply cloning.
> --what is known as using the copy contructor in C++. Even in C++, using "new" doesn't imply using a copy constructor.
> The only advantage in C# using :ICloneable is that the base > class :ICloneable makes replicating a duplicate class (a clone) much > easier The advantage to ICloneable is that the object provides a defined interface to clone itself. In many cases, this would be the _only_ way to clone an object, as the user of the object has no direct access to private members that also have to be cloned as part of the cloning process.
> --no need to instantiate every composite object in such a class, > to duplicate every member variable in it and set it to a value, etc, > using 'new', etc, 'by hand'. Instead, you just pick either a deep or > shallow clone and :ICloneable does everything for you, behind the > scenes. You don't have the option. You can't make a shallow clone of an object from outside the object. You can only clone an object if it provides a cloning method, and that cloning method is usually the Clone() method of the ICloneable interface, which should provide a deep copy of the object.
> I hope I didn't needlessly complicate this thread... Well, I'd say that given that the behavior requested in the original question is impossible when you clone an object, by introducing the topic of cloning to the thread you very much have complicated this thread.
Pete
raylopez99 - 28 Sep 2007 20:53 GMT > > I think Clone is just shorthand for what is known as a "copy > > constructor" in C++. > > Well, it's not. Clone is a specific reference to the Clone() method > found in the ICloneable interface. Analogy, not exact definition.
> > Usually, in managed languages you "pass the > > pointer" (C++) or "pass the reference" (C#), so indeed clone is not > > often used, but it's used more often than you might think. > > No, it's not. It's used as infrequently as we think. No, you're wrong. But let's move on.
> > That's > > because everytime you use "new", and other lines of code, essentially [quoted text clipped - 3 lines] > object requires the use of "new", but "new" very much does not imply > cloning. Not what I said--"and other lines of code" meaning you are essentially replicating ICloneable, such as if you were to make a copy constructor in C# (which is possible with version 2.0, since earlier this year I did just that).
> > --what is known as using the copy contructor in C++. > > Even in C++, using "new" doesn't imply using a copy constructor. Not what I said, see above.
> > The only advantage in C# using :ICloneable is that the base > > class :ICloneable makes replicating a duplicate class (a clone) much [quoted text clipped - 4 lines] > to clone an object, as the user of the object has no direct access to > private members that also have to be cloned as part of the cloning process. Thanks for that information. "In many cases", meaning in some cases I am correct. So I should drop the word "only" in "only advantage" and should have said "an advantage".
> > --no need to instantiate every composite object in such a class, > > to duplicate every member variable in it and set it to a value, etc, [quoted text clipped - 6 lines] > cloning method, and that cloning method is usually the Clone() method of > the ICloneable interface, which should provide a deep copy of the object. Usually, but a lot of people don't use ICloneable and simply "do it by hand", the long way. That was my point.
> > I hope I didn't needlessly complicate this thread... > [quoted text clipped - 3 lines] > > Pete But the behavior requested in the original thread is nearly trivial. O = O. Trivial. Much better to show that by judicious placing of ICloneable you can make another copy of a reference or tracking pointer, which is much more useful IMO in a real program--since it can be a "snapshot" of a mutable class, a placeholder, something returned by a method (such as a tracking pointer factory method), etc.
Sorry if I confused you Pete, but frankly I've been coding in C# for just a few weeks now, and I'm beginning to see that I know as much or more than some of the "veterans" in this NG! :-) I'm not saying I know more than you and Jon however...not yet.
How do I get the [C# MVP] tag BTW? Can I just add it to my sig file or does MSFT have a certification program or something? I'll just add it and see if I can get away with it.
Ray Lopez [C# MVP]
Peter Duniho - 28 Sep 2007 21:38 GMT >>> I think Clone is just shorthand for what is known as a "copy >>> constructor" in C++. >> Well, it's not. Clone is a specific reference to the Clone() method >> found in the ICloneable interface. > > Analogy, not exact definition. Except that we are using the term as it is exactly, precisely defined in the context of .NET.
If you are going to misuse terms that have specific definitions, you need to at least be clear that you are doing so intentionally.
> [...] >>> That's [quoted text clipped - 8 lines] > in C# (which is possible with version 2.0, since earlier this year I > did just that). You may have had some other intent specifically in mind. However, you're not communicating your intent very well. I've never seen any useful code that just calls "new" and doesn't have any other lines of code. So your phrase "everytime [sic] you use 'new', and other lines of code" is redundant and doesn't in any way distinguish from the basic use of "new".
In any case, as I've already pointed out, in most cases only the class itself is able to make a true clone of itself. You can't just call "new" and then do some other stuff to create a clone from outside the class.
That's why ICloneable exists.
Beyond that, if what you meant to write was "every time you use 'new' and exactly duplicate the data in an instance of a class, essentially you are cloning", well...I have to agree with that, but don't find it a useful statement since it's so obviously true. You might as well write "every time you clone a data structure, essentially you are cloning".
> [...] >>> The only advantage in C# using :ICloneable is that the base [quoted text clipped - 8 lines] > am correct. So I should drop the word "only" in "only advantage" and > should have said "an advantage". IMHO, it is more that the use of the word "only" implies that the advantage you're talking about is somehow trivial or unnecessary. The "advantage" of which you write _is_ in fact the primary advantage of ICloneable, but it's not so much an "advantage" as it is a critical requirement for allowing a class to be cloned in a general-purpose way.
"Advantage" implies that there's some other way to do it, but which might not be as good by some measure. But in this case, there's really not any other way to do what ICloneable provides.
Yes, you could do it via a copy constructor, but doing by interface allows for a consistent way for code to refer to an object as "something that can be cloned" without having to know anything else about it (like its type, required for calling a constructor). And you certainly cannot in general clone an instance of a class from outside the class itself.
> Usually, but a lot of people don't use ICloneable and simply "do it by > hand", the long way. That was my point. Who are these "lot of people" of which you speak? How many situations have you seen in which people clone objects by hand? How, in fact, are these people able to do that, when the class encapsulates critical information data not available to the code creating the clone?
>>> I hope I didn't needlessly complicate this thread... >> Well, I'd say that given that the behavior requested in the original >> question is impossible when you clone an object, by introducing the >> topic of cloning to the thread you very much have complicated this thread. > > But the behavior requested in the original thread is nearly trivial. You may consider it trivial. However, it's a very specific kind of behavior, commonly used in a variety of situations. And, most importantly here, it is mutually exclusive with the topic of cloning.
> O = O. Trivial. Well, that statement, "O = O", is not only trivial, it's pointless and has nothing to do with the original post or anything else in this thread. No code here has been posted where a variable was assigned to itself.
> Much better to show that by judicious placing of > ICloneable you can make another copy of a reference or tracking > pointer, First of all, making a copy of a reference is easy. You just copy the reference. But that has nothing to do with cloning, so I'll assume what you really meant to write was "you can make another copy of an instance referred to by a reference". That out of the way...
That's not "better" at all. It's an entirely different technique, and cannot in any way be implemented through cloning. As I have tried to explain repeatedly, by cloning an object you completely block the ability to do what was requested in the original post.
> which is much more useful IMO in a real program--since it can > be a "snapshot" of a mutable class, a placeholder, something returned > by a method (such as a tracking pointer factory method), etc. I have no idea why you think a technique that prevents the behavior specifically being asked for is "much more useful". Cloning certainly has its place, but in this context is entirely inappropriate.
> Sorry if I confused you Pete, You have not confused me. You are making the thread confusing for others who may try to read it and understand how to implement the behavior requested by the original poster.
> but frankly I've been coding in C# for > just a few weeks now, and I'm beginning to see that I know as much or > more than some of the "veterans" in this NG! :-) Only been coding in C# for a few weeks? So when you wrote that "earlier this year I did just that" (in reference to making a copy constructor), you really meant "earlier this month"?
Frankly, it is pretty obvious from your posts that you know a lot less about C# and programming in general that you think you do. It is true that you frequently refuse to accept that you have made errors; in that sense, it's clear you aren't receptive to the feedback you need in order to have a correct understanding of the situation.
But make no mistake: that doesn't mean your feelings of superiority are justified. All it means that you don't have the ability to do any self-reflection in which you might discover mistakes you have made.
Basically, when you're wrong you just have no capability to understand that you're wrong, so the fact that you're wrong continues to be a mystery to you.
It's not that you're wrong all the time. But you are wrong a lot more than you are willing to admit. This gives you an overinflated sense of competence.
Pete
Doug Semler - 28 Sep 2007 21:51 GMT >> > I think Clone is just shorthand for what is known as a "copy >> > constructor" in C++. [quoted text clipped - 3 lines] > > Analogy, not exact definition. Not to hijack, but it's even a ban analogy. Clone means something completely different than a copy constructor. Clone doesn't necessarily have to return the type of object being cloned. Just a compatible type.
Copy constructors are actually constructors of the specific object type. You can't return a "compatible" type from a copy constructor....because the constructor doesn't return anything.
>> > Usually, in managed languages you "pass the >> > pointer" (C++) or "pass the reference" (C#), so indeed clone is not [quoted text clipped - 3 lines] > > No, you're wrong. But let's move on. From the lurking i've done in this group in the past 3 years or so, I'm probably one of maybe 2 people here that uses Clone() on a regular basis. But that's because I have specific support requirements for it dealing with revertability and serialization (don't look at me....i wans't the original author <g>)
>> > That's >> > because everytime you use "new", and other lines of code, essentially [quoted text clipped - 8 lines] > in C# (which is possible with version 2.0, since earlier this year I > did just that). You are NEVER cloning when you use new. In either C# or C++. You are creating a new memory instance and calling the constructor. Now whether the constructors have been declared to accept a parameter and copy data from the parameter's instance is different story.
I don't really think you understand when a C++ copy constructor is actually does or when it's used. Or the requirements on it. Or what happens when you don't define one (which basically is a "MemberwiseClone()".
>> > The only advantage in C# using :ICloneable is that the base >> > class :ICloneable makes replicating a duplicate class (a clone) much [quoted text clipped - 5 lines] >> private members that also have to be cloned as part of the cloning >> process. Well, you could expose a function that retunrs the results of MemberwiseClone(), but that only ever makes a shallow copy. Depending on the requirements, a cloned copy may be required to be a deep copy. In addition, there are certain situations where the object is managing unmanaged memory...
> Thanks for that information. "In many cases", meaning in some cases I > am correct. So I should drop the word "only" in "only advantage" and > should have said "an advantage". There are four advantages to IClonable that i can think of. Nothing to do with making it "easier" to actually copy the object. Zeroth is that it is a well documented common framework interface that all .net programmers have access to. First is it allows you to override the behavior of MemberwiseClone() to make deep copies of an object. The second is to return a object that is type compable rather than of the type itself. The third is when your objects are holding unmanaged references that have to be handled in very specific (and sometimes very ODD) manners. I'm sure Jon and Pete can and a couple others can think of other more esoteric reasons or even non esoteric reasons...
>> > --no need to instantiate every composite object in such a class, >> > to duplicate every member variable in it and set it to a value, etc, [quoted text clipped - 6 lines] >> cloning method, and that cloning method is usually the Clone() method of >> the ICloneable interface, which should provide a deep copy of the object. (Or provide a "ShallowClone") public method that just returns the results of this.MemberwiseClone()) :)
> Usually, but a lot of people don't use ICloneable and simply "do it by > hand", the long way. That was my point. Huh? Do what the long way? Copy the object? How can I make a complete copy from outside the object without access to private fields?
Cloning of large objects is a PITA and error prone. I would ALWAYS provide a "one stop" clone method of some sort if requirements of the object dictate...and never leave it up to the user of the object.
(And I've finally gotten out of the habit of creating constructors that take an instance of the type as a parameter in order to act as a C++ copy constructor) <g>
 Signature Doug Semler, MCPD a.a. #705, BAAWA. EAC Guardian of the Horn of the IPU (pbuhh). The answer is 42; DNRC o- Gur Hfrarg unf orpbzr fb shyy bs penc gurfr qnlf, abbar rira erpbtavmrf fvzcyr guvatf yvxr ebg13 nalzber. Fnq, vfa'g vg?
raylopez99 - 29 Sep 2007 21:56 GMT > >> > I think Clone is just shorthand for what is known as a "copy > >> > constructor" in C++. [quoted text clipped - 7 lines] > completely different than a copy constructor. Clone doesn't necessarily > have to return the type of object being cloned. Just a compatible type. OK, but you're over my head here--I don't know what 'compatible type' means. Perhaps an exception to the rule (that proves the rule).
> Copy constructors are actually constructors of the specific object type. > You can't return a "compatible" type from a copy constructor....because the > constructor doesn't return anything. OK, again, you're trying to make an exception (this 'compatible type' business) into the general rule. Not good form, but I see your point (that you found an exception).
> From the lurking i've done in this group in the past 3 years or so, I'm > probably one of maybe 2 people here that uses Clone() on a regular basis. > But that's because I have specific support requirements for it dealing with > revertability and serialization (don't look at me....i wans't the original > author <g>) Perhaps. Or it could be that with tracking pointers (references) in C#, you don't really need a copy constructor aka clone--you just pass the pointer/ reference.
> You are NEVER cloning when you use new. In either C# or C++. You are > creating a new memory instance and calling the constructor. Now whether the > constructors have been declared to accept a parameter and copy data from the > parameter's instance is different story. I think you're being too clever by half here. First you say "NEVER", then you essentially acknowledge my point, that you clone using new (and doing other things as well, but using new).
> I don't really think you understand when a C++ copy constructor is actually > does or when it's used. Or the requirements on it. Or what happens when > you don't define one (which basically is a "MemberwiseClone()". No, I do understand the difference between a shallow copy and a deep copy in C++, and the problem of aliasing. Thanks.
> >> > The only advantage in C# using :ICloneable is that the base > >> > class :ICloneable makes replicating a duplicate class (a clone) much [quoted text clipped - 11 lines] > addition, there are certain situations where the object is managing > unmanaged memory... I see that you pointed out a contradiction in Pete's post (the words quoted with ">" are Pete's not mine)--good for you, as it shows Pete is not like the Pope, infallible! :-) But again, seems like you're taking a weird exception "Well, you could..." into a general rule. After all, in fairness to Pete, Pete said "In MANY cases" (emphasis added).
> There are four advantages to IClonable that i can think of. Nothing to do > with making it "easier" to actually copy the object. Zeroth is that it is a > well documented common framework interface that all .net programmers have > access to. OK, I got that, thanks, it makes sense.
> First is it allows you to override the behavior of > MemberwiseClone() to make deep copies of an object. Uh, are you aware (I think not) that ICloneable can have TWO variants? A shallow copy (MemberwiseClone) and a deep copy ([Serializable] then use BinaryFormatter()?). I take it you are, but from your posts you seem to not understand this, unless I'm misreading you, which may be the case.
> The second is to return > a object that is type compable rather than of the type itself. Sorry but I don't understand what "type compable" is. Let's table this one.
> The third is > when your objects are holding unmanaged references that have to be handled > in very specific (and sometimes very ODD) manners. I'm sure Jon and Pete > can and a couple others can think of other more esoteric reasons or even non > esoteric reasons... ODD means nothing. Metaphysics.
> > Usually, but a lot of people don't use ICloneable and simply "do it by > > hand", the long way. That was my point. > > Huh? Do what the long way? Copy the object? How can I make a complete > copy from outside the object without access to private fields?
>From inside the object. WOrk with me Doug! :-)
> Cloning of large objects is a PITA and error prone. I would ALWAYS provide > a "one stop" clone method of some sort if requirements of the object > dictate...and never leave it up to the user of the object. That's nice. Makes sense, kind of like (analogy here) always using error correction 'try/catch' everywhere.
> (And I've finally gotten out of the habit of creating constructors that take > an instance of the type as a parameter in order to act as a C++ copy > constructor) <g> Yeah, I think I understand--when I first switched from C++ I kept trying to replicate copy constructors in C#, but I gave up since I concluded that they're rarely used, since most of the time you pass the pointer and don't destroy it, so no need to copy it.
RL
Doug Semler - 30 Sep 2007 15:34 GMT >> >> > I think Clone is just shorthand for what is known as a "copy >> >> > constructor" in C++. [quoted text clipped - 10 lines] > OK, but you're over my head here--I don't know what 'compatible type' > means. Perhaps an exception to the rule (that proves the rule). No. Not it's not an exception. Two completely different paradigms. Clone loosens the restrictions on what is required to be returned. Since a constructor (copy or otherwise) doesn't "return" anything, it's always of the type being constructed.
>> Copy constructors are actually constructors of the specific object type. >> You can't return a "compatible" type from a copy constructor....because [quoted text clipped - 4 lines] > business) into the general rule. Not good form, but I see your point > (that you found an exception). No, I am not. You're making a general rule where there is none.
>> From the lurking i've done in this group in the past 3 years or so, I'm >> probably one of maybe 2 people here that uses Clone() on a regular basis. [quoted text clipped - 7 lines] > C#, you don't really need a copy constructor aka clone--you just pass > the pointer/ reference. No. That would be very bad in the cases to which i am referring. I need copies of the object so that I can revert them back to the original form. I also need copies because in some cases the serialization routine is being completed asynchronously, but it the block it is accessing can be locked. It's faster to make a copy and work with that copy in a differnt thread than block the caller. When these copies are made I need them to follow specific rules as well.
>> You are NEVER cloning when you use new. In either C# or C++. You are >> creating a new memory instance and calling the constructor. Now whether [quoted text clipped - 6 lines] > then you essentially acknowledge my point, that you clone using new > (and doing other things as well, but using new). No, you don't clone using new. You are calling a specific constructor when you use new. But "new" in and of itself just allocates memory (well, ok, exception: placement new in C++<g>). It is the semantics of the constructor that is specified that actually does the work. However, C++ defines a specific constructor that is called in certain situations (called the "copy constructor"). By default, this basically does what the object.MemberwiseClone() does. However, I can explicitly create one and have it do NOTHING if I want it to.
>> >> > The only advantage in C# using :ICloneable is that the base >> >> > class :ICloneable makes replicating a duplicate class (a clone) much [quoted text clipped - 19 lines] > After all, in fairness to Pete, Pete said "In MANY cases" (emphasis > added). Take a chill pill...it was a JOKE.
>> There are four advantages to IClonable that i can think of. Nothing to >> do [quoted text clipped - 13 lines] > from your posts you seem to not understand this, unless I'm misreading > you, which may be the case. What the hell are you talking about? There is no variance. MemberwiseClone() makes a shallow copy (for blittable members, they are bitwise copies, for references they are just the same reference). It returns an object of the type being cloned. IClonable leaves the implementation up to the object. It can return a shallow copy, a deep copy. The only other requirement is that the function returns a COMPATIBLE type of the object being cloned (which, in all cases that i can think of, is the type) I don't know what you're talking about with the serialize/binaryformatter thing, unless you are saying that makes a deep copy. But try doing that trick on an object that's holding a pointer to unmanaged memory and see how well that works...
>> The second is to return >> a object that is type compable rather than of the type itself. > > Sorry but I don't understand what "type compable" is. Let's table > this one. Let's not. Look it up, it's important. And let's not try to claim to be a C# MVP or otherwise until you know what this means.
>> The third is >> when your objects are holding unmanaged references that have to be [quoted text clipped - 5 lines] > > ODD means nothing. Metaphysics. Odd. Meaning not normal. Nothing metaphysical about it. Some of the code I have to deal with is translated from hardware microcode implementations, which means I end up having to deal with memory in very odd manners. And some of these objects are required to be cloneable (for reasons irrelevant to this discussion)
>> > Usually, but a lot of people don't use ICloneable and simply "do it by >> > hand", the long way. That was my point. [quoted text clipped - 3 lines] > >>From inside the object. WOrk with me Doug! :-) Well, if I only wanted to do it from inside the object (shallow), I'd just call MemberwiseClone(). If i needed a deep copy I'd create a private member function. If I wanted to expose it to the outside world, I'd just implement the interface IClonable and exposed the already written functionality. Until I do that last part, the object is unclonable from the outside world (either shallow or deep).
>> Cloning of large objects is a PITA and error prone. I would ALWAYS >> provide [quoted text clipped - 3 lines] > That's nice. Makes sense, kind of like (analogy here) always using > error correction 'try/catch' everywhere. No way, it's called code reuse. If I want the users of my object to be able to clone it, I'll give them that opportunity by implementing the IClonable interface. Otherwise, they can't. That doesn't stop me from writing a "one-stop-shop" that implements a private clone method.
(and i don't know what exactly your "analogy" means..)
 Signature Doug Semler, MCPD a.a. #705, BAAWA. EAC Guardian of the Horn of the IPU (pbuhh). The answer is 42; DNRC o- Gur Hfrarg unf orpbzr fb shyy bs penc gurfr qnlf, abbar rira erpbtavmrf fvzcyr guvatf yvxr ebg13 nalzber. Fnq, vfa'g vg?
Family Tree Mike - 29 Sep 2007 02:34 GMT > How do I get the [C# MVP] tag BTW? Can I just add it to my sig file > or does MSFT have a certification program or something? I'll just add > it and see if I can get away with it. > > Ray Lopez > [C# MVP] I'm not sure how one becomes an MVP, but I'm pretty sure you aren't doing it right.
Michael S - 08 Oct 2007 15:16 GMT >> How do I get the [C# MVP] tag BTW? Can I just add it to my sig file >> or does MSFT have a certification program or something? I'll just add [quoted text clipped - 6 lines] > it > right. At least he is consistant. :)
- Michael Starberg
Free MagazinesGet these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...
|
|
|