macos 类的objective-c 默认初始化方法?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/4542628/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-21 07:30:21  来源:igfitidea点击:

objective-c default init method for class?

objective-cmacosinitialization

提问by Alex

I have two differing methods for initializing my objective-c class. One is the default, and one takes a configuration parameter. Now, I'm pretty green when it comes to objective-c, but I've implemented these methods and I'm wondering if there's a better (more correct/in good style) way to handle initialization than the way I have done it. Meaning, did I write these initialization functions in accordance with standards and good style? It just doesn't feel right to check for the existence of selfPtrand then return based on that.

我有两种不同的方法来初始化我的 Objective-c 类。一种是默认值,一种采用配置参数。现在,当涉及到objective-c 时,我很不满意,但是我已经实现了这些方法,我想知道是否有比我完成的方法更好(更正确/风格更好)的方法来处理初始化. 意思是,我是否按照标准和良好的风格编写了这些初始化函数?检查 的存在selfPtr然后根据它返回感觉是不对的。

Below are my class header and implementation files. Also, if you spot anything else that is wrong or evil, please let me know. I am a C++/Javascript developer who is learning objective-c as hobby and would appreciate any tips that you could offer.

下面是我的类头文件和实现文件。另外,如果您发现任何其他错误或邪恶的内容,请告诉我。我是一名 C++/Javascript 开发人员,正在将 Objective-C 作为爱好学习,并希望您能提供任何提示。

#import <Cocoa/Cocoa.h>

// class for raising events and parsing returned directives

@interface awesome : NSObject {
 // silence is golden. Actually properties are golden. Hence this emptiness.
}

// properties
@property (retain) SBJsonParser* parser;
@property (retain) NSString* eventDomain;
@property (retain) NSString* appid

// constructors
-(id) init;
-(id) initWithAppId:(id) input;

// destructor
-(void) dealloc;


@end


#import "awesome.h"
#import "JSON.h"


@implementation awesome



- (id) init {
 if (self = [super init]) {
  // if init is called directly, just pass nil to AppId contructor variant
  id selfPtr = [self initWithAppId:nil];
 }

 if (selfPtr) {
  return selfPtr;
 } else {
  return self;
 }
}

- (id) initWithAppId:(id) input {
 if (self = [super init]) {
  if (input = nil) {
   input = [[NSString alloc] initWithString:@"a369x123"];
  }
  [self setAppid:input];
  [self setEventDomain:[[NSString alloc] initWithString:@"desktop"]];
 }
 return self;
}

// property synthesis
@synthesize parser;
@synthesize appid;
@synthesize eventDomain;

// destructor
- (void) dealloc {
 self.parser = nil;
 self.appid = nil;
 self.eventDomain = nil;
 [super dealloc];
}

@end

Thanks!

谢谢!

回答by d11wtq

When one initializer simply performs the more complex initializer with some default parameters, call it as such:

当一个初始化器简单地使用一些默认参数执行更复杂的初始化器时,这样调用它:

-(id)init {
  return [self initWithAppID:nil];
}

-(id)initWithAppID:(id)input {
  if (self = [super init]) {
    /* perform your post-initialization logic here */
  }
  return self;
}

Usually you try to make one of the initializers the "designated initializer", meaning it's the one that always gets invoked. In this case that's -initWithAppID:.

通常,您尝试使初始化器之一成为“指定初始化器”,这意味着它始终被调用。在这种情况下,就是-initWithAppID:.

回答by ughoavgfhw

Your init method should call the preferred initializer, initWithAppId:, instead of the super implementation. Then the initWithAppId calls the super implementation, as it does. Also, in initWithAppId:, you have if(input = nil), which will always set input to nil and evaluate to YES. Here are the proper implementations.

您的 init 方法应该调用首选初始化程序 initWithAppId:,而不是超级实现。然后 initWithAppId 调用超级实现,就像它一样。此外,在 initWithAppId: 中,您有 if(input = nil),它将始终将输入设置为 nil 并评估为 YES。以下是正确的实现。

- (id)init {
    return [self initWithAppId:nil];
}
- (id)initWithAppId:(id)input {
    if((self = [super init])) {
        if(input == nil) input = @"a369x123";
        self.appid = input;
        self.eventDomain = @"desktop";
    }
    return self;
}

回答by jer

To be honest, I see this as a moot point. Your second initialization method makes no sense when receiving a nil argument (plus you have a logic problem in your conditional checking if input is nil). What I would do in this case, is provide one initialization method, and two factory class methods which act in the usual way: Return autoreleased instances, and in one of them, provide your default value.

老实说,我认为这是一个有争议的问题。在接收 nil 参数时,您的第二个初始化方法没有意义(另外,如果输入为 nil,您的条件检查存在逻辑问题)。在这种情况下,我会做的是提供一个初始化方法和两个以通常方式运行的工厂类方法:返回自动释放的实例,并在其中之一中提供您的默认值。

For instance, declare a class method:

例如,声明一个类方法:

+ (awesome*)awesome;
+ (awesome*)awesomeWithAppId:(id)foo;

and in your implementation for +awesomefor instance, write it like this:

+awesome例如,在您的实现中,这样写:

+ (awesome*)awesome
{
    return [[[awesome alloc] initWithAppId:@"a369x123"] autorelease];
}

And likewise, in your awesomeWithAppId:something like this:

同样,在你awesomeWithAppId:这样的事情中:

+ (awesome*)awesomeWithAppId:(id)foo
{
    return [[[awesome alloc] initWithAppId:foo] autorelease];
}

Then again, this may just be me.

再说一次,这可能只是我。

回答by WrightsCS

The defaultwill be whichever one you choose to call,

default会是你选择调用哪一个,

[awesome alloc] init];
[awesome alloc] initWithAppId:ID];