Cloning derived objects whose base objects have many fields

K

K.K.

Suppose I have a class called Vehicle with many fields. Now I make a new
class derived from Vehicle called Car. I'd like to make a method to copy the
data from a Vehicle instance to a Car instance. Is writing a long series of
assignments in a Clone() statement my only option?

I know that I can write a Clone method using MemberwiseClone(), but my
understanding is that the object created by MemberwiseClone is of the same
type.
 
N

Nicholas Paldino [.NET/C# MVP]

K.K.,

This isn't a good idea. What if you have a class, Airplane, derived
from Vehicle, and then pass that to a Car instance to be cloned? An
Airplane definitely isn't a car, so it shouldn't really work.

What is it that you are trying to do? If anything, a Car should clone a
Car, or anything deriving from Car.

Hope this helps.
 
K

K.K.

Nicholas,

Sorry, I guess I wasn't clear. I'm saying that I have an instance of a
Vehicle (the base class). Now I'd like to construct a new instance of a Car
whose base-class fields are equal to the Vehicle instance. I guess it's sort
of like a copy constructor for Car, except that I'm not using another Car as
the basis for the copying, but rather a Vehicle.

Hope that makes a little more sense. Thanks again!

- KK


Nicholas Paldino said:
K.K.,

This isn't a good idea. What if you have a class, Airplane, derived
from Vehicle, and then pass that to a Car instance to be cloned? An
Airplane definitely isn't a car, so it shouldn't really work.

What is it that you are trying to do? If anything, a Car should clone a
Car, or anything deriving from Car.

Hope this helps.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
Suppose I have a class called Vehicle with many fields. Now I make a new
class derived from Vehicle called Car. I'd like to make a method to copy
the
data from a Vehicle instance to a Car instance. Is writing a long series
of
assignments in a Clone() statement my only option?

I know that I can write a Clone method using MemberwiseClone(), but my
understanding is that the object created by MemberwiseClone is of the same
type.
 
N

Nicholas Paldino [.NET/C# MVP]

KK,

It does, but your logic is wrong, because a Vehicle can be something
that is not a Car, but a Car is always a Vehicle.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
Nicholas,

Sorry, I guess I wasn't clear. I'm saying that I have an instance of a
Vehicle (the base class). Now I'd like to construct a new instance of a
Car
whose base-class fields are equal to the Vehicle instance. I guess it's
sort
of like a copy constructor for Car, except that I'm not using another Car
as
the basis for the copying, but rather a Vehicle.

Hope that makes a little more sense. Thanks again!

- KK


in
message news:%[email protected]...
K.K.,

This isn't a good idea. What if you have a class, Airplane, derived
from Vehicle, and then pass that to a Car instance to be cloned? An
Airplane definitely isn't a car, so it shouldn't really work.

What is it that you are trying to do? If anything, a Car should
clone a
Car, or anything deriving from Car.

Hope this helps.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
Suppose I have a class called Vehicle with many fields. Now I make a
new
class derived from Vehicle called Car. I'd like to make a method to
copy
the
data from a Vehicle instance to a Car instance. Is writing a long
series
of
assignments in a Clone() statement my only option?

I know that I can write a Clone method using MemberwiseClone(), but my
understanding is that the object created by MemberwiseClone is of the same
type.
 
K

K.K.

But suppose I have an instance of something that is /just/ a Vehicle, as in
"Vehicle v = new Vehicle();". Such an instance doesn't represent a Car, or a
Boat, or an Airplane (yet). What I'm asking is how to place this information
/into/ a new Car, Boat, or Airplane.

Nicholas Paldino said:
KK,

It does, but your logic is wrong, because a Vehicle can be something
that is not a Car, but a Car is always a Vehicle.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
Nicholas,

Sorry, I guess I wasn't clear. I'm saying that I have an instance of a
Vehicle (the base class). Now I'd like to construct a new instance of a
Car
whose base-class fields are equal to the Vehicle instance. I guess it's
sort
of like a copy constructor for Car, except that I'm not using another Car
as
the basis for the copying, but rather a Vehicle.

Hope that makes a little more sense. Thanks again!

- KK


in
message news:%[email protected]...
K.K.,

This isn't a good idea. What if you have a class, Airplane, derived
from Vehicle, and then pass that to a Car instance to be cloned? An
Airplane definitely isn't a car, so it shouldn't really work.

What is it that you are trying to do? If anything, a Car should
clone a
Car, or anything deriving from Car.

Hope this helps.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

"K.K." <kkaitan [at] gmail [dot] com> wrote in message
Suppose I have a class called Vehicle with many fields. Now I make a
new
class derived from Vehicle called Car. I'd like to make a method to
copy
the
data from a Vehicle instance to a Car instance. Is writing a long
series
of
assignments in a Clone() statement my only option?

I know that I can write a Clone method using MemberwiseClone(), but my
understanding is that the object created by MemberwiseClone is of the same
type.
 
N

Nicholas Paldino [.NET/C# MVP]

KK,

That's the thing, you wouldn't be able to, because your Vehicle should
be abstract, you shouldn't be able to have an instance of it. It should
always be an instance of a derived type.

--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
But suppose I have an instance of something that is /just/ a Vehicle, as
in
"Vehicle v = new Vehicle();". Such an instance doesn't represent a Car, or
a
Boat, or an Airplane (yet). What I'm asking is how to place this
information
/into/ a new Car, Boat, or Airplane.

in
message news:[email protected]...
KK,

It does, but your logic is wrong, because a Vehicle can be something
that is not a Car, but a Car is always a Vehicle.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
Nicholas,

Sorry, I guess I wasn't clear. I'm saying that I have an instance of a
Vehicle (the base class). Now I'd like to construct a new instance of a
Car
whose base-class fields are equal to the Vehicle instance. I guess it's
sort
of like a copy constructor for Car, except that I'm not using another Car
as
the basis for the copying, but rather a Vehicle.

Hope that makes a little more sense. Thanks again!

- KK


"Nicholas Paldino [.NET/C# MVP]" <[email protected]>
wrote
in
message K.K.,

This isn't a good idea. What if you have a class, Airplane, derived
from Vehicle, and then pass that to a Car instance to be cloned? An
Airplane definitely isn't a car, so it shouldn't really work.

What is it that you are trying to do? If anything, a Car should
clone
a
Car, or anything deriving from Car.

Hope this helps.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

"K.K." <kkaitan [at] gmail [dot] com> wrote in message
Suppose I have a class called Vehicle with many fields. Now I make a
new
class derived from Vehicle called Car. I'd like to make a method to
copy
the
data from a Vehicle instance to a Car instance. Is writing a long
series
of
assignments in a Clone() statement my only option?

I know that I can write a Clone method using MemberwiseClone(), but my
understanding is that the object created by MemberwiseClone is of
the
same
type.
 
K

K.K.

Nick,

I don't think I'm explaining myself very well. Maybe this example will clear
it up:
class BankAccount
{
public string Name;
public int AccountNumber;
// ... many other details
}

class SavingsAccount : BankAccount
{
public int InterestRate;
}

class CheckingAccount : BankAccount
{
public int MaximumChecks;
}
<<<<

Going by the above, my questions are:

1.) Is it wrong for BankAccount to not be abstract?
2.) A SavingsAccount is only marginally different from a CheckingAccount,
and both are BankAccount objects. What if I had a new instance of a
CheckingAccount and I wanted to copy the BankAccount portion of an existing
SavingsAccount instance into the new CheckingAccount instance? How might I
do this, without simply making a long series of assignment statements? (Or
is that the only way?)
3.) As question (2), but now suppose that I just have a BankAccount object
instead of a SavingsAccount. How might I copy the BankAccount instance
fields into the new CheckingAccount?

Thanks again for all your help so far.
 
D

Dan Bass

Nicholas,

I'm not sure I agree... Just because an object is a parent to a derived
class, it doesn't mean it has to be an abstract class or interface.
I derived from a Form for a scanner, and called it ScanForm. It "is a" form,
but has extended functionality, this doesn't mean that Form must therefore
be abstract.

The vehicle example does suggest that the parent will have no use other than
defining a template from which other classes inherit, but it's not
definitively so.

Dan.



Nicholas Paldino said:
KK,

That's the thing, you wouldn't be able to, because your Vehicle should
be abstract, you shouldn't be able to have an instance of it. It should
always be an instance of a derived type.

--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
But suppose I have an instance of something that is /just/ a Vehicle, as
in
"Vehicle v = new Vehicle();". Such an instance doesn't represent a Car,
or a
Boat, or an Airplane (yet). What I'm asking is how to place this
information
/into/ a new Car, Boat, or Airplane.

in
message news:[email protected]...
KK,

It does, but your logic is wrong, because a Vehicle can be something
that is not a Car, but a Car is always a Vehicle.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

"K.K." <kkaitan [at] gmail [dot] com> wrote in message
Nicholas,

Sorry, I guess I wasn't clear. I'm saying that I have an instance of a
Vehicle (the base class). Now I'd like to construct a new instance of
a
Car
whose base-class fields are equal to the Vehicle instance. I guess
it's
sort
of like a copy constructor for Car, except that I'm not using another Car
as
the basis for the copying, but rather a Vehicle.

Hope that makes a little more sense. Thanks again!

- KK


"Nicholas Paldino [.NET/C# MVP]" <[email protected]>
wrote
in
message K.K.,

This isn't a good idea. What if you have a class, Airplane, derived
from Vehicle, and then pass that to a Car instance to be cloned? An
Airplane definitely isn't a car, so it shouldn't really work.

What is it that you are trying to do? If anything, a Car should
clone
a
Car, or anything deriving from Car.

Hope this helps.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

"K.K." <kkaitan [at] gmail [dot] com> wrote in message
Suppose I have a class called Vehicle with many fields. Now I make
a
new
class derived from Vehicle called Car. I'd like to make a method to
copy
the
data from a Vehicle instance to a Car instance. Is writing a long
series
of
assignments in a Clone() statement my only option?

I know that I can write a Clone method using MemberwiseClone(), but my
understanding is that the object created by MemberwiseClone is of
the
same
type.
 
D

Dan Bass

1).
This depends entirely on the context in which BankAccount is used.
If a BankAccount must be either Savings or Checking, then definately yes,
BankAccount must be abstract.

2)
You can't copy between two different types. A string can't be copied into an
int... It can, however, be converted. What I'd suggest for each class is
that if you need to cast/convert between two different accounts, then in
your SavingsAccount class, have a "ToCheckingAccount()" method. Conversely,
in the CheckingAccount, have a "ToSavingsAccount()" method. These functions
would return an instance of an object that has had the fields populated
according to the source. You'd have to reference each field in these objects
that you want to pass back to your accounts function.

3)
This relies on the answer to (1). If a BankAccount must be Savings or
Checking, then you should never have an instance of BankAccount.

Note that you can have the following though:

BankAccount myBankAccount = (BankAccount)new SavingsAccount();

This would allow you to create a base class variable, then depending what
you want, you could assign either a Savings or Checking account to it, and
access methods that are declared in the parent, but overridden in the
children.

HTH.

Dan.
 
N

Nicholas Paldino [.NET/C# MVP]

Dan,

You are right, this isn't definitive, but based on the example the OP
initially gave, it would seem so =)


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

Dan Bass said:
Nicholas,

I'm not sure I agree... Just because an object is a parent to a derived
class, it doesn't mean it has to be an abstract class or interface.
I derived from a Form for a scanner, and called it ScanForm. It "is a"
form, but has extended functionality, this doesn't mean that Form must
therefore be abstract.

The vehicle example does suggest that the parent will have no use other
than defining a template from which other classes inherit, but it's not
definitively so.

Dan.



Nicholas Paldino said:
KK,

That's the thing, you wouldn't be able to, because your Vehicle should
be abstract, you shouldn't be able to have an instance of it. It should
always be an instance of a derived type.

--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

K.K. said:
But suppose I have an instance of something that is /just/ a Vehicle, as
in
"Vehicle v = new Vehicle();". Such an instance doesn't represent a Car,
or a
Boat, or an Airplane (yet). What I'm asking is how to place this
information
/into/ a new Car, Boat, or Airplane.

in
message KK,

It does, but your logic is wrong, because a Vehicle can be
something
that is not a Car, but a Car is always a Vehicle.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

"K.K." <kkaitan [at] gmail [dot] com> wrote in message
Nicholas,

Sorry, I guess I wasn't clear. I'm saying that I have an instance of
a
Vehicle (the base class). Now I'd like to construct a new instance of
a
Car
whose base-class fields are equal to the Vehicle instance. I guess
it's
sort
of like a copy constructor for Car, except that I'm not using another
Car
as
the basis for the copying, but rather a Vehicle.

Hope that makes a little more sense. Thanks again!

- KK


"Nicholas Paldino [.NET/C# MVP]" <[email protected]>
wrote
in
message K.K.,

This isn't a good idea. What if you have a class, Airplane,
derived
from Vehicle, and then pass that to a Car instance to be cloned? An
Airplane definitely isn't a car, so it shouldn't really work.

What is it that you are trying to do? If anything, a Car should
clone
a
Car, or anything deriving from Car.

Hope this helps.


--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

"K.K." <kkaitan [at] gmail [dot] com> wrote in message
Suppose I have a class called Vehicle with many fields. Now I make
a
new
class derived from Vehicle called Car. I'd like to make a method
to
copy
the
data from a Vehicle instance to a Car instance. Is writing a long
series
of
assignments in a Clone() statement my only option?

I know that I can write a Clone method using MemberwiseClone(),
but
my
understanding is that the object created by MemberwiseClone is of
the
same
type.
 
B

Bruce Wood

K.K.

I would solve this problem by providing an alternate constructor on
Car:

public Car (Vehicle baseVehicle, ... other initialization arguments ...
) : base(baseVehicle)
{
.... copy other arguments in here...
}

This requires only that you provide a constructor in Vehicle that takes
a Vehicle, and yes, you have to write a bunch of assignment statements.
The good news is that you have to do it only once, in the base class.

I would do it this way because it is not, in fact, a Clone operation.
You're instantiating a new Car based on an existing Vehicle.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top