2012-06-07 51 views
0

我发现这个代码返回可变其中返回值应该是不可变的

-(NSString *) genRandStringLength: (int) len { 

    NSMutableString *randomString = [NSMutableString stringWithCapacity: len]; 

    for (int i=0; i<len; i++) { 
     [randomString appendFormat: @"%C", [letters characterAtIndex: arc4random() % [letters length]]]; 
    } 

    return randomString; 
} 

是它确定传递一个可变对象,其中,所述结果是不可变的?

我们应该怎么做?

return [randomString copy]; 

return randomString; 

回答

4

从技术上讲,它是返回一个NSMutableString而不是NSString没有问题。由于前者是后者的子类,因此NSMutableString实例支持NSString所做的一切。例如,如果你看看Cocoa,你会注意到,很多alloc/init方法返回你想创建的类的子类的一个实例。

在你的特殊情况下,如果方法返回一个可变字符串,我看不出什么问题,因为该字符串是在该方法中本地创建的,并且未在该类的其他位置使用。

通常,如果这些对象是返回它们的类的ivars /属性,则应该避免返回可变对象。如果你做了这样的事情,方法的调用者可以发现返回的对象是可变的,然后改变其内容,而不通知对象的“拥有”实例关于变化。

另外请注意,如果你想返回一个不可变的对象,return [randomString copy];只在ARC和垃圾收集下是正确的。对于手动内存管理,它应该是return [[randomString copy] autorelease];return [NSString stringWithString:randomString];

0

你可以这样做: -

-(NSString *) genRandStringLength: (int) len 
{ 
    NSMutableString *randomString = [NSMutableString stringWithCapacity: len]; 

    for (int i=0; i<len; i++) { 
    [randomString appendFormat: @"%C", [letters characterAtIndex: arc4random() % [letters length]]]; 
    } 

    NSString *immutableString = [NSString stringWithString:randomString]; 

    //OR 

    NSString *immutableString = (NSString *)randomString; 

    return immutableString; 
}