Objective-C が float や double などの代わりに NSNumber を使用することにした理由がわかりません。この型はディスク上でどのように表されますか?
3 に答える
NSNumber
はフリーダイヤルでブリッジされていCFNumber
ます。Core Foundation の最近の実装でCFNumber
は、タグ付きポインターです。これにより、オブジェクトとして扱うことができますが、オブジェクトのオーバーヘッドはまったくありません。代わりに、値はオブジェクト ポインターにエンコードされます (実際にはポインターではありません)。
Lion のタグ付きポインタと高速パス CFNumber 整数を参照してください。
NSNumber
はの子孫でNSObject
あるため、どこにでも移動id
できます:NSarray
、、NSDictionary
など。などのプリミティブは、から継承しないため、コレクションなどに参加できないint
ためdouble
、これらのクラスに参加できません。NSObject
の内部を推測するとしNSNumber
ます。ユニオンとタイプセレクターフィールドだと思います。ただし、カプセル化の美しさにより、NSNumber
その表現について最初に知らなくても(そしてその知識を逃さずに)プログラムを成功させることができます。
覚えておくべきことの 1 つは、Objective-C は C のスーパーセットであるため、プリミティブ型 (float、double など) のNSNumber
代わりに使用することを決定したのではなく、それらに加えて使用することを決定したことです。の機能が必要ない場合はNSNumber
、プリミティブ型を使用して、オブジェクトの作成/破棄のオーバーヘッドを節約してください。iOS の多くの関数 (特に配列型関数)は、オブジェクト(の子孫)でのみ機能します。したがって、何らかのタイプの数値をこれらの関数のいずれかに渡したい場合は、そのオブジェクト表現が必要です。ここで出番です。NSObject
NSNumber
ドキュメントを引用するにはNSNumber
:
NSNumber は、任意の C スカラー (数値) 型として値を提供する NSValue のサブクラスです。これは、signed または unsigned char、short int、int、long int、long long int、float、または double または BOOL として値を設定およびアクセスするための一連のメソッドを定義します。(数値オブジェクトは、それらが作成されたときの型を必ずしも保持しないことに注意してください。) また、2 つの NSNumber オブジェクトの順序を決定するための compare: メソッドも定義します。
内部的には、実際の値は、格納する値に応じて、整数または浮動小数点数 (Jay が説明するタグ付きポインターまたはオブジェクトの共用体のいずれか) として格納されることに注意してください。「32.1」のような数値を格納しようとすると、浮動小数点数として格納され、それを取得すると、「32.09999999999999」のような値が得られる可能性が高いため、これを知っておくことが重要です。
ディスクに保存する限り、これを行う必要がある場合は、通常、保存してencodeWithCoder
取得し、initWithEncoder
ディスクに保存して後で読み戻すことを目的とした形式に変換します。