每个视图类都有多个init方法 - 已经作为UIView的一部分包含的方法,然后是其他方法 - 并且每个方法都以相同的方式设置相同的元素。因此,我通常让它们都运行[self initialSetup];
方法,其中包括设置所有这些元素。
我遇到的问题是,如果一个子类也有一个initialSetup方法,它将覆盖超类的initialSetup方法,因此超类必须将该方法公开才能仍然起作用。这会导致组织问题,因为永远不应该从init调用该方法,因此没有理由公开。
答案 0 :(得分:2)
将initialSetup
的名称更改为initialSetupClassName
- 子类,即使他们意外使用了相同的模式,也不会使用与具有不同类名的名称相同的名称。
你也可以为你不想被调用的私有方法使用“_”前缀,但是子类也可以这样做。
答案 1 :(得分:2)
你遇到了一个问题,那就是没有完美的解决办法。你理想情况下的方法是一种方法,它不能在正常意义上进行子类化,只能用于那种确切类型的类的实例。
如果这是一种风险,通常的做法似乎是将类名合并到setup方法中。因此,initialSetup
代替myViewSubclassInitialSetup
,而不是NSAssert([self isMemberOfClass:[ThisClass class]],
@"IniitalSetup called by sub- or superclass")
。
您还可以在方法的顶部添加类似的内容:
{{1}}
如果子类或超类最终调用init方法,那么调试版本将引发异常。这将为您提供断点和堆栈跟踪的位置,以便您可以非常快速地找到问题。
它不会向您的发布版本添加任何代码。
答案 2 :(得分:2)
听起来你错过了一个指定的初始化程序。将一个初始化程序指定为实际执行设置的正式初始化程序,并让所有其他初始化程序仅通过某种程度的自定义调用它。通常,指定的初始值设定项将是最详细的初始值设定项 - 例如,如果您有init
,initWithName:
,initWithName:age:
和initAsFiveYearOldNamed:
,则指定的初始值设定项将为{{ 1}}和其他初始化程序只会在适当填充参数的情况下调用该方法。
答案 3 :(得分:1)
不幸的是Objective C
没有提供一种以“干净”的方式实现这一目标的方法。理想的解决方案是受保护的方法。但这在Objective C
Apple在创建UIGestureRecognizer
时遇到了这个问题。有些方法他们真的不想被某人调用,但必须被子类覆盖。他们选择处理此问题的方法是创建一个单独的头文件(UIGestureRecognizerSubclass.h
),其中包含原始UIGestureRecognizer
的类别和那些“受保护”方法。附加标题仅由子类导入(即用于子类化目的)。有关详细信息,请参阅UIGestureRecognizer Class Reference。
当然,这并不妨碍任何人滥用额外的头文件,但至少它清楚地表明了你的意图并保持你的代码结构良好。此外,当您使用该类时,您不会因其他方法的自动完成而“烦恼”。
我个人只使用额外的标题,如果没有人直接调用它是非常重要的。在大多数情况下,我认为使用公共方法并记下它的含义是可以的。 iOS框架也有许多这样的情况。 F.E. UIViewController
的{{1}}等许多方法