Class Factory Methods implementation

后端 未结 2 322
自闭症患者
自闭症患者 2021-01-15 01:08

So I am working my way through the Apple documentation of objective-C (before jumping into iphone development). One of the exercises states that I should create a designated

相关标签:
2条回答
  • 2021-01-15 01:40

    Declare and implement a new designated initializer used to create an XYZPerson using a specified first name, last name and date of birth...

    You are correct in the declaration but your implementation is recursive, since it's calling itself. Do something like

    //.h
    -(id)initWithNameAndDob:(NSString *)fName last:(NSString *)lName birth:(NSDate *) dob;
    //.m
    -(id)initWithNameAndDob:(NSString *)fName last:(NSString *)lName birth:(NSDate *)dob{
        if(self = [super init]) {
            // use the parameters to do something, eg.
            _fName = fName; // assuming you have an ivar called _fName 
            _lName = lName; // assuming you have an ivar called _lName
            _dob = dob; // assuming you have an ivar called _dob
        }
        return self;
    }
    

    Then

    ...along with a suitable class factory method.

    A factory method is a class method that produces an instance of the object. The most common implementation is to have it to allocate and initialize a new instance of the object and return it.

    //.h
    +(instancetype)personWithNameAndDob:(NSString *)fName last:(NSString *)lName birth:(NSDate *) dob {
    
    
    //.m
    +(instancetype)personWithNameAndDob:(NSString *)fName last:(NSString *)lName birth:(NSDate *) dob {
    return [[XYZPerson alloc] initWithNameAndDob:fName last:lName birth:dob];
    }
    

    Finally

    Don’t forget to override init to call the designated initializer.

    Since your designed initializer is initWithNameAndDob:last:birth: your init implementation must call it. The parameters of the designed initializer have to be a reasonable default, in this case nil is fine.

    -(id)init {
         return [self initWithNameAndDob:nil last:nil birth:nil];
     }
    

    As a final remark I'd like to point out that your naming convention for the initializer is not that good. A more suitable and readable one would be

    -(id)initWithFirstName:(NSString *)fName lastName:(NSString *)lName dateOfBirth:(NSDate *) dob;
    
    0 讨论(0)
  • 2021-01-15 01:54

    Excellent explanation by Gabriele Petronella but there is problem.

    +(instancetype)personWithNameAndDob:(NSString *)fName last:(NSString *)lName birth:(NSDate *) dob {
    return [[XYZPerson alloc] initWithNameAndDob:fName last:lName birth:dob];
    }
    
    It should be replaced with 
    +(instancetype)personWithNameAndDob:(NSString *)fName last:(NSString *)lName birth:(NSDate *) dob {
    return [[self alloc] initWithNameAndDob:fName last:lName birth:dob];
    }
    

    Rule: Don’t refer to your own class by name, because you don’t know what the concrete class will be. You’ll inadvertently chop off the ability to extend and override the class through subclassing. Instead, To allocate an instance in a class’s factory method: [self alloc] Reference: http://qualitycoding.org/factory-method/

    0 讨论(0)
提交回复
热议问题