无用的init怎么办?

发布于 2024-12-13 08:56:49 字数 460 浏览 0 评论 0原文

这就是我目前的 init

- (id)init 
{
    self = [super init];

    if (self) {
        self.url = [[NSURL alloc] init];
        self.blurb = [[NSString alloc] init];
        self.author = [[NSString alloc] init];
    }

    return self;
}

它什么也不做,但我有另一个名为 initWithObject: 的方法,它将使用它的参数来填充实例变量 urlblurbauthor。我不知道应该用这个 init 做什么。我应该抛出异常吗?我还有什么其他选择?

This is currently what I have for my init,

- (id)init 
{
    self = [super init];

    if (self) {
        self.url = [[NSURL alloc] init];
        self.blurb = [[NSString alloc] init];
        self.author = [[NSString alloc] init];
    }

    return self;
}

It does nothing, but I have another method called initWithObject: that will use its argument to fill up the instance variables url, blurb, and author. I don't know what I should be doing with this init. Should I throw an exception? What other options do I have?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

明月夜 2024-12-20 08:56:49

如果您想重写标准 -init 方法,您可以返回 nil (如果您不希望使用 -init)或执行以下操作:

- (instancetype)init
{
    return [self initWithObject:nil];
}

如果您想完全停止使用 -init ,您可以将其标记为不可用属性或使用 NSAssert:

// .h
// ...

- (instancetype)init UNAVAILABLE_ATTRIBUTE;

// ...

// .m
- (instancetype)init
{
    NSAssert(NO, @"This method should not be used");
    return nil;
}

您可以使用 UNAVAILABLE_ATTRIBUTENSAssert(),但是如果如果您使用 UNAVAILABLE_ATTRIBUTE,则需要某种 -init 实现,即使它只是返回 nil

If you want to override your standard -init method you could either return nil (if you do not want -init to be used) or do:

- (instancetype)init
{
    return [self initWithObject:nil];
}

If you want to stop the use of -init completely you can tag it as an unavailable attribute or use NSAssert:

// .h
// ...

- (instancetype)init UNAVAILABLE_ATTRIBUTE;

// ...

// .m
- (instancetype)init
{
    NSAssert(NO, @"This method should not be used");
    return nil;
}

You can use either UNAVAILABLE_ATTRIBUTE or NSAssert(), but if you use UNAVAILABLE_ATTRIBUTE you need some kind of implementation of -init, even if it just returns nil.

舂唻埖巳落 2024-12-20 08:56:49

您不必拥有普通的 init — 您只需拥有 initWithObject: 方法即可。如果您正在进行任何在 80% 的时间内保持不变的基本设置,或者如果您的所有初始化程序中都有一些通用代码,则可以覆盖 init,但这不是必需的。

还可以考虑将您的 initWithObject: 名称更改为更具体,例如 initWithPost: (我假设这是某种基于您的 ivars 的博客条目获取器)所以想要什么对象就更明显了。

You don't have to have a plain init—you can simply have your initWithObject: method. If you're doing any basic setup that will remain the same 80% of the time, or if you have some common code in all your initializers, you can override init, but you are not required to.

Also consider changing your initWithObject: name to be more specific, to something like initWithPost: (I'm assuming this is some kind of blog-entry fetcher based on your ivars) so it's more apparent what object is desired.

我一向站在原地 2024-12-20 08:56:49

我认为你误解了你读到的内容。我不认为你会抛出异常。你可以;然而,泄漏内存。如果你的 initWithObject: 方法看起来像这样:

- (id)initWithObject:(id)obj {
     if ((self = [self init])) {
              self.url=[obj url];
              self.blurb=[obj blurb];
              self.author=[obj author];
     }
     return self;
}

那么你就完美了。如果您的对象是使用 -init 实例化的,并且您使用了已分配的变量(假设它是真实的),则可能会出现异常。因此,在后续方法中,请务必在使用对象之前检查它们是否存在。

如果您使用 -init 而不是 -initWithObject 创建对象,则可能会引发异常:

- (void)dealloc {
         [url release];
         [blurb release];
         [author release];
         [super dealloc];
}

I think you misinterpreted what you read. I don't think you would throw an exception. You could; however, leak memory. If your initWithObject: method looks like this:

- (id)initWithObject:(id)obj {
     if ((self = [self init])) {
              self.url=[obj url];
              self.blurb=[obj blurb];
              self.author=[obj author];
     }
     return self;
}

And you would be perfectly fine. You could get an exception if your object was instantiated with -init and you used a variable which was assigned, assuming it was real. So in your subsequent methods be sure to check that the objects exist before using them.

If you made your object with -init rather than -initWithObject this could throw an exception:

- (void)dealloc {
         [url release];
         [blurb release];
         [author release];
         [super dealloc];
}
心意如水 2024-12-20 08:56:49

Apple 为 Cocoa 编程制定的规则是每个类必须有一个初始化方法,即 "指定初始化器”。该类的每个其他初始化程序都必须调用该 DI* DI 本身必须调用超类的 DI 通常,具有最多参数的初始化程序(最完整地指定新对​​象的状态)是 DI

在您的情况下,使用裸 initinitWithObject:,第二个可能是 DI,因此您需要重写 init 来调用 initWithObject:< /code> 有一些默认值参数:

- (id) init {

    return [self initWithObject:[Object objectWithURL:[NSURL URLWithString:@"http://www.apple.com"]
                                                blurb:@""
                                               author:@""]];
}

这将产生一种虚拟对象,它使用无用的数据正确初始化。 (在 ARC 之外,请务必注意默认参数的内存管理——您想要使用自动释放/无主对象。)

*有时 initWithCoder 会出现异常:

The rule that Apple has established for Cocoa programming is that every class must have one initializer method which is the "Designated Initializer". Every other initializer for the class must call that D.I.* The D.I. itself must call the superclass's D.I. Generally, the initializer with the greatest number of arguments (the one that most completely specifies the state of the new object) is the D.I.

In your case, with the bare init, and initWithObject:, the second would likely be the D.I. You would therefore override init to call initWithObject: with some default argument:

- (id) init {

    return [self initWithObject:[Object objectWithURL:[NSURL URLWithString:@"http://www.apple.com"]
                                                blurb:@""
                                               author:@""]];
}

This will result in a sort of dummy object, which is correctly initialized with useless data. (Outside of ARC, be sure to watch the memory management of the default argument(s) -- you want to use an autoreleased/unowned object(s).)

*Sometimes an exception is made for initWithCoder:.

那一片橙海, 2024-12-20 08:56:49

如果您不想调用任何方法并且不希望子类支持任何方法,那么在调试构建中抛出异常是完全合理的。

If you have any method that you don't want called and that you don't want your subclass to support, throwing an exception in a Debug build is perfectly reasonable.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文