我离开了原版,所以人们可以理解评论的背景。希望这个例子能更好地帮助解释我的目标。
我可以在Obj-C中创建一个具有文件范围可见性的类吗?
例如,我在NSNotificationCenter上编写了一个方法方块类别,它会在deallocs时自动删除任何观察者。
我在实现中使用了一个帮助器类,为了防止名称冲突,我设计了一个命名方案。该类别是NSNotificationCenter(WJHAutoRemoval),因此此代码中使用的私有帮助程序类被命名为...
WJH_NSNotification_WJHAutoRemoval__Private__BlockObserver
那是满口的,目前我只是这样做......
#define BlockObserver WJH_NSNotification_WJHAutoRemoval__Private__BlockObserver
并在代码中使用BlockObserver。
但是,我不喜欢这个解决方案。
我想告诉编译器,“嘿,这个类名为Bar。我的代码将作为Bar访问它,但我真的是唯一需要知道的。自己生成一个时髦的名字,或者更好,甚至不输出符号,因为我是唯一应该关心的人。“
对于普通的C,我会“静态”而对于C ++“namespace {}”
在Obj-C中执行此操作的首选/最佳/唯一方法是什么?
原始问题
我想在另一个实现中使用一个帮助器类。但是,我不想要外部联系。现在,我只是让助手类名称非常独特,所以我不会得到重复的链接符号。
我可以使用静态C函数,但我想编写一个辅助类,只在编译单元内部具有链接器可见性。
例如,我想在多个.m文件中使用以下内容,每个“Helper”对该文件都是唯一的,并且没有其他编译单元具有链接器访问权限。如果我在10个不同的文件中有这个,我将有10个单独的类。
@interface Helper : NSObject
...
@end
@implementation Helper : NSObject
...
@end
我无法在任何地方找到任何暗示,而我在界面/实现中加上“静态”的微弱尝试都是错误的。
谢谢!
答案 0 :(得分:3)
我不相信你会因为Objective-C Runtime而能够做你想做的事。所有类都加载到运行时,具有相同名称的多个类将相互冲突。
Objective-C是一种动态语言。与在编译时绑定方法调用的其他语言不同,Objective-C在调用(每次调用)时执行方法解析。运行时在运行时中找到该类,然后在类中查找该方法。运行时不能支持具有相同名称的不同类,而Objective-C不支持命名空间来分隔您的类。
如果你的Helper
类在每种情况下都不同,那么它们将需要不同的类名(多个具有相同名称的类对我来说听起来不错,在任何语言中)。如果它们是相同的,那么为什么要单独声明它们呢?
我认为你需要重新考虑你的策略,因为你要做的事情听起来不是Objective-C或Cocoa。
答案 1 :(得分:0)
没有办法让课程“隐藏”。正如mttrb所说,类可以通过运行时通过名称访问。这与C和C ++不同,其中class只是链接器解析为地址的符号。每个类都被注入到类层次结构中。
但我还不清楚为什么你还需要这个。如果您有私有类WJHAutoRemovalHelper
或其他任何内容,那么除了私有Apple类或私有第三方框架类之外,似乎不太可能与其他任何人发生冲突。没有理由采取英雄的长度来使其模糊不清;用WJHAutoRemoval
作为前缀应该足以让它独一无二。你正试图解决一些更深层次的问题吗?
关于“私人”课程的问题,如果你手工完成,你所建议的是可能的,但实际上没有理由。您可以生成一个随机的唯一类名,在其上调用objc_allocateClassPair()
和objc_registerClassPair
,然后在运行时将其分配给Class
变量。 (然后调用class_addMethod
和class_addIvar
来构建它。然后您可以在需要时随时通过该变量引用它。当然,在运行时通过调用objc_getClassList
仍可访问它,但是系统中的类名不会有符号。
但这是很多工作和复杂性,没有任何好处。 ObjC并没有花太多时间担心像C ++那样保护程序。它使用命名约定和编译器警告来告诉您何时出错,并期望作为一名优秀的程序员,您将避免做错事。