开发者

NSCopying & Inheritance

Please have a look on following code :------- .h

@interface BankAccount : NSObject<NSCopying>
{
    double accountBalance;
    long accountNumber;
    NSString *CustomerName;
    NSString *AccountType;
}

-(void) setAccount: (long) y andBalance: (double) x;
-(void) setCustomerName: (NSString*) name andAccountType: (NSString*) type;
-(i开发者_如何学编程d)copyWithZone:(NSZone *)zone;

@end

@interface Savings : BankAccount
{
    int number;
    NSString *Offer;
}
-(void) setSavingNumber: (uint8_t) num andOffer: (NSString*) offer;
-(id)copyWithZone:(NSZone *)zone;
@end

---------- .m

@implementation BankAccount

-(void) setAccount: (long) y andBalance: (double) x
{
    accountNumber = y;
    accountBalance = x;
}
-(void) setCustomerName: (NSString*) name andAccountType: (NSString*) type
{
    CustomerName = name;
    AccountType = type;
}

-(id)copyWithZone:(NSZone *)zone
{
    BankAccount *accountCopy = [[BankAccount allocWithZone: zone] init];
    [accountCopy setAccount: accountNumber andBalance: accountBalance];
    [accountCopy setCustomerName:CustomerName andAccountType:AccountType];
    return accountCopy;
}

@end

@implementation Savings
-(void) setSavingNumber: (uint8_t) num andOffer: (NSString*) offer
{
    number = num;
    Offer = offer;
}

-(id)copyWithZone:(NSZone *)zone
{
    Savings * clone = [super copyWithZone:zone];
    [clone setSavingNumber:number andOffer:Offer];************** error *********
    return clone;
}

@end

When run this code::::::

Savings* account1;
Savings* account2;

account1 = [[Savings alloc] init];
[account1 setAccount:10 andBalance:1000.10];
[account1 setCustomerName:[NSString stringWithFormat:@"%@",@"Deepak"] andAccountType:[NSString stringWithFormat:@"%@",@"Savings"]];
[account1 setSavingNumber:2001 andOffer:@"Bad"];    
account2 = [account1 copy];
#

i dont know what is wrong with the code please help me. thanks in advance.

Thanks Deepak


Your base copyWithZone: method should look like this:

-(id)copyWithZone:(NSZone *)zone {
    // change this line to use [self class]
    BaseClass *base = [[[self class] allocWithZone:zone] init];

    // copy base members:
    // ...

    return base;
}

Your derived copyWithZone: methods should look like this:

-(id)copyWithZone:(NSZone *)zone {
    DerivedClass *derived = [super copyWithZone:zone];

    // copy derived members:
    // ...

    return derived;
}

Also make sure sure you are making deep copies of strong references and shallow copies of weak references. Thus to for example copy members of type NSString and NSArray (each one with strongly referenced members and one with weak) do:

derived.strongString    = [[strongString copyWithZone:zone] autorelease];
derived.weakString      = weakString;
derived.strArrWStrVals  = [[strArrWStrVals copyWithZone:zone] autorelease];
derived.strArrWWeakVals = [[[NSArray allocWithZone:zone]
                            initWithArray:strArrWWeakVals] autorelease];
derived.weakArray       = weakArray;

(Usually weak members are also assigned/retained and strong variables are copied.)

Take note that because of this you should not use initWithMyself: type methods to copy data.


Ok first, your test code is bad because you set a saving number of 2001 in an 8 bit integer. Second, your code does not run because you're trying to call setSavingNumber:andOffer: on a BankAccount instead of an Saving object so it can't find the selector for this method at run time. Thanks David for pointing that out.

When implementing BankAccount::copyWithZone, you used the alloc-init and you returned the object which is fine. When implementing Savings::copyWithZone, you call super copyWithZone. What you get is an object of type BankAccount so you cannot use setSavingNumber:andOffer: on it. Since you used the alloc-init in the base class, you should also use the alloc-init and setMethods in the Savings class.

To avoid duplicating code, I'd recomment implementing an initWithBankAccount in BankAccount and the same in Savings.

Then in the copyWithZone, you'd have

return [[BankAccount allocWithZone:zone] initWithBankAccount:self];

and

return [[Savings allocWithZone:zone] initWithSavings:self];

Although you must make sure that in initWithSavings you call either

self = [super initWithBankAccount:savings];

or you call straight init and you copy the base member initialization.

Have a look at Implementing object copy from Memory management programming guide.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜