2

我创建了一个NSObject用作模型的子类。

在此范围内,我有一些可以在此之外访问的公共方法。

在实现文件中,我还有一些像这样的私有方法:

+(void)publicMethod {
    // I am public
}


-(void)privateMethod {
    // I am private 
}

但是,我无法从公共方法中调用私有方法。即以下不起作用:

[self privateMethod];

这是预期的行为吗?我的 NSObject 子类(用作模型)中的所有方法都应该公开吗?

4

2 回答 2

2

编辑:请注意此答案不完整。这个问题涉及调用类方法的实例方法,我在写答案时没有抓住。但即使它没有回答这个问题,它仍然是如何模仿 Objective-C 中公共和私有方法的使用的一个例子。


在 Objective-C 中没有公共和私有方法之类的东西,但是您可以通过不将它们放在公共头文件中来“隐藏”实例方法。

这就是苹果的做法。NSObject、UIView、NSString 等,都有一堆“私有”的方法。因为他们不是私人的。它们根本不会在您包含在应用程序中的头文件中公开。

如果你的类有一个外部世界不可见的实例或类方法,你仍然可以自己声明它——如果你知道原型——在你的代码中然后访问它们。

我这样做的方法是创建两个头文件。一种用于公共方法,一种用于私有方法。假设这是一个公共库,我只会包含带有“公共”方法的头文件供其他开发人员使用。

另一方面,在我的项目中,我可以包含“私有”标头,它包含私有和公共方法,并且我可以访问我需要的所有内容。

一个例子是这个类,它必须有 methods:foobar. foo是公开的,bar也是私有的。

“公共”标头 - 被称为MyCustomClass.h如下所示:

@interface MyCustomClass

- (void)foo;

@end

然后我在另一个头文件中创建了一个类扩展 - 它被称为MyCustomClass+Private.h,它看起来像这样。这也是放置实例变量的好地方,因此它们也不会暴露于“外部世界”。

@import "MyPublicClass.h"

@interface MyPublicClass () {

    NSInteger _myIvar;

}

- (void)bar;

@end

现在在类实现中 - 这被称为MyCustomClass.m我实现了一切。请注意,我包括私有头文件。

@import "MyPublicClass+Private.h"

@implementation MyPublicClass

- (void)bar { /* Private Method */

    /* Do something */

}

- (void)foo {

    [self bar];

}

@end

解决方案

现在,每当我将 MyCustomClass 子类化时,我首先还要为该类创建一个私有标头 - 它导入它的超类的私有标头。子类的公共标头只导入它的超类的公共标头。

这种方式既暴露给子类,foobar暴露给外人——因为你不会把你的私有头文件放在你的库中——如果你正在做的话。

对你的例子的评论

在过去,你可以做你想做的事,并摆脱编译器警告。但现在 ARC 并不满足,并引发编译器错误。这是因为 ARC 需要知道返回类型,因此它可以对其进行释放/保留,以便正确管理您的应用程序的内存。

更简单的解决方案

一种更简单的方法也可以是在子类的实现中抛出超类扩展——使用超类的“私有”方法原型。但这有一个缺点,如果你改变你的超类的行为,你需要遍历你放置扩展的每个地方。所以我不会推荐它。

最后

希望这可以澄清并帮助您。祝你好运!

于 2013-09-02T22:17:49.080 回答
0

publicMethod是一个类方法。此方法中的类也是如此self,而不是实例。并且该类没有实现privateMethod,因为它是一个实例方法。

于 2013-09-02T21:31:02.103 回答