Objective-Cで気になったもの(クラス拡張)
2018/01/04
最近はiOSアプリの勉強をしています。 都合により、SwiftじゃなくてObjective-Cで書いています。 iOSアプリ開発では言語というよりSDKであるUIKitの使い方を覚えるほうが大事みたいなので、Objective-Cで勉強したとしても無駄にはなりません。
この記事ではObjective-Cで書いていて気になったものをちょっとメモ。
疑問
XcodeでViewControllerを作成するとヘッダーファイルと.m
の実装ファイルができる。
ヘッダーの方には@interface
のクラス宣言が書かれていて、.m
の方で@implementation
を使って実際にメソッドの処理を記述するようになっています。
しかし、自動生成して作ったファイルには実装のほうにも@interface
がある。
これはなに?
// HogeController.m
#import "HogeViewController.h"
@interface HogeViewController ()
@end
// ↑これ
@implementation HogeViewController
/*
...
*/
@end
クラス宣言がダブってエラーになったりしないのでしょうか。というかここの中身は、なにも書かなくていいの?
そのうえ、クラス名のあとに()
がついていて、ただのクラス宣言と違った特殊な雰囲気を醸し出しています。お前はいったいなんなんだ。
クラス拡張
調べてみれば、これはクラス拡張というものらしいです。
Objective-Cには既存のクラスにあとづけでメソッドを追加できるカテゴリという機能があります。
カテゴリは@interface NSString (カテゴリ名)
のように、@interface
のクラス名のあとにカテゴリをカッコで囲むようになっています。
そのカッコの中身が無くなったのがクラス拡張です。
実際にはカテゴリとクラス拡張はまったく違う機能みたいなのですが、今のところ似たようなものと理解しておけばいいと思います。
要するに、すでにクラス宣言した内容にあとづけでいろいろなメソッドやプロパティを追加できるのがクラス拡張です。
使いみち
privateなメソッドやプロパティを宣言するために使います。
ヘッダーファイルの@interface
内に書かれている内容は、importしたファイルからは丸見えになります。
しかし、内部の処理は隠蔽して外部には見せたくないときもありますよね。
そういうときはクラス拡張の中に書くことで、ヘッダーファイルにはそのメソッドなどの情報がなくなりますので、内部だけで使用することができます。
JavaやC++ではprivate
を付ければいいのですが、見た目も特殊なObjective-Cではこういうテクニック?を使うみたいです。