]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - docs/ObjectiveCLiterals.rst
Vendor import of clang RELEASE_350/final tag r216957 (effectively, 3.5.0 release):
[FreeBSD/FreeBSD.git] / docs / ObjectiveCLiterals.rst
1 ====================
2 Objective-C Literals
3 ====================
4
5 Introduction
6 ============
7
8 Three new features were introduced into clang at the same time:
9 *NSNumber Literals* provide a syntax for creating ``NSNumber`` from
10 scalar literal expressions; *Collection Literals* provide a short-hand
11 for creating arrays and dictionaries; *Object Subscripting* provides a
12 way to use subscripting with Objective-C objects. Users of Apple
13 compiler releases can use these features starting with the Apple LLVM
14 Compiler 4.0. Users of open-source LLVM.org compiler releases can use
15 these features starting with clang v3.1.
16
17 These language additions simplify common Objective-C programming
18 patterns, make programs more concise, and improve the safety of
19 container creation.
20
21 This document describes how the features are implemented in clang, and
22 how to use them in your own programs.
23
24 NSNumber Literals
25 =================
26
27 The framework class ``NSNumber`` is used to wrap scalar values inside
28 objects: signed and unsigned integers (``char``, ``short``, ``int``,
29 ``long``, ``long long``), floating point numbers (``float``,
30 ``double``), and boolean values (``BOOL``, C++ ``bool``). Scalar values
31 wrapped in objects are also known as *boxed* values.
32
33 In Objective-C, any character, numeric or boolean literal prefixed with
34 the ``'@'`` character will evaluate to a pointer to an ``NSNumber``
35 object initialized with that value. C's type suffixes may be used to
36 control the size of numeric literals.
37
38 Examples
39 --------
40
41 The following program illustrates the rules for ``NSNumber`` literals:
42
43 .. code-block:: objc
44
45     void main(int argc, const char *argv[]) {
46       // character literals.
47       NSNumber *theLetterZ = @'Z';          // equivalent to [NSNumber numberWithChar:'Z']
48
49       // integral literals.
50       NSNumber *fortyTwo = @42;             // equivalent to [NSNumber numberWithInt:42]
51       NSNumber *fortyTwoUnsigned = @42U;    // equivalent to [NSNumber numberWithUnsignedInt:42U]
52       NSNumber *fortyTwoLong = @42L;        // equivalent to [NSNumber numberWithLong:42L]
53       NSNumber *fortyTwoLongLong = @42LL;   // equivalent to [NSNumber numberWithLongLong:42LL]
54
55       // floating point literals.
56       NSNumber *piFloat = @3.141592654F;    // equivalent to [NSNumber numberWithFloat:3.141592654F]
57       NSNumber *piDouble = @3.1415926535;   // equivalent to [NSNumber numberWithDouble:3.1415926535]
58
59       // BOOL literals.
60       NSNumber *yesNumber = @YES;           // equivalent to [NSNumber numberWithBool:YES]
61       NSNumber *noNumber = @NO;             // equivalent to [NSNumber numberWithBool:NO]
62
63     #ifdef __cplusplus
64       NSNumber *trueNumber = @true;         // equivalent to [NSNumber numberWithBool:(BOOL)true]
65       NSNumber *falseNumber = @false;       // equivalent to [NSNumber numberWithBool:(BOOL)false]
66     #endif
67     }
68
69 Discussion
70 ----------
71
72 NSNumber literals only support literal scalar values after the ``'@'``.
73 Consequently, ``@INT_MAX`` works, but ``@INT_MIN`` does not, because
74 they are defined like this:
75
76 .. code-block:: objc
77
78     #define INT_MAX   2147483647  /* max value for an int */
79     #define INT_MIN   (-2147483647-1) /* min value for an int */
80
81 The definition of ``INT_MIN`` is not a simple literal, but a
82 parenthesized expression. Parenthesized expressions are supported using
83 the `boxed expression <#objc_boxed_expressions>`_ syntax, which is
84 described in the next section.
85
86 Because ``NSNumber`` does not currently support wrapping ``long double``
87 values, the use of a ``long double NSNumber`` literal (e.g.
88 ``@123.23L``) will be rejected by the compiler.
89
90 Previously, the ``BOOL`` type was simply a typedef for ``signed char``,
91 and ``YES`` and ``NO`` were macros that expand to ``(BOOL)1`` and
92 ``(BOOL)0`` respectively. To support ``@YES`` and ``@NO`` expressions,
93 these macros are now defined using new language keywords in
94 ``<objc/objc.h>``:
95
96 .. code-block:: objc
97
98     #if __has_feature(objc_bool)
99     #define YES             __objc_yes
100     #define NO              __objc_no
101     #else
102     #define YES             ((BOOL)1)
103     #define NO              ((BOOL)0)
104     #endif
105
106 The compiler implicitly converts ``__objc_yes`` and ``__objc_no`` to
107 ``(BOOL)1`` and ``(BOOL)0``. The keywords are used to disambiguate
108 ``BOOL`` and integer literals.
109
110 Objective-C++ also supports ``@true`` and ``@false`` expressions, which
111 are equivalent to ``@YES`` and ``@NO``.
112
113 Boxed Expressions
114 =================
115
116 Objective-C provides a new syntax for boxing C expressions:
117
118 .. code-block:: objc
119
120     @( <expression> )
121
122 Expressions of scalar (numeric, enumerated, BOOL) and C string pointer
123 types are supported:
124
125 .. code-block:: objc
126
127     // numbers.
128     NSNumber *smallestInt = @(-INT_MAX - 1);  // [NSNumber numberWithInt:(-INT_MAX - 1)]
129     NSNumber *piOverTwo = @(M_PI / 2);        // [NSNumber numberWithDouble:(M_PI / 2)]
130
131     // enumerated types.
132     typedef enum { Red, Green, Blue } Color;
133     NSNumber *favoriteColor = @(Green);       // [NSNumber numberWithInt:((int)Green)]
134
135     // strings.
136     NSString *path = @(getenv("PATH"));       // [NSString stringWithUTF8String:(getenv("PATH"))]
137     NSArray *pathComponents = [path componentsSeparatedByString:@":"];
138
139 Boxed Enums
140 -----------
141
142 Cocoa frameworks frequently define constant values using *enums.*
143 Although enum values are integral, they may not be used directly as
144 boxed literals (this avoids conflicts with future ``'@'``-prefixed
145 Objective-C keywords). Instead, an enum value must be placed inside a
146 boxed expression. The following example demonstrates configuring an
147 ``AVAudioRecorder`` using a dictionary that contains a boxed enumeration
148 value:
149
150 .. code-block:: objc
151
152     enum {
153       AVAudioQualityMin = 0,
154       AVAudioQualityLow = 0x20,
155       AVAudioQualityMedium = 0x40,
156       AVAudioQualityHigh = 0x60,
157       AVAudioQualityMax = 0x7F
158     };
159
160     - (AVAudioRecorder *)recordToFile:(NSURL *)fileURL {
161       NSDictionary *settings = @{ AVEncoderAudioQualityKey : @(AVAudioQualityMax) };
162       return [[AVAudioRecorder alloc] initWithURL:fileURL settings:settings error:NULL];
163     }
164
165 The expression ``@(AVAudioQualityMax)`` converts ``AVAudioQualityMax``
166 to an integer type, and boxes the value accordingly. If the enum has a
167 :ref:`fixed underlying type <objc-fixed-enum>` as in:
168
169 .. code-block:: objc
170
171     typedef enum : unsigned char { Red, Green, Blue } Color;
172     NSNumber *red = @(Red), *green = @(Green), *blue = @(Blue); // => [NSNumber numberWithUnsignedChar:]
173
174 then the fixed underlying type will be used to select the correct
175 ``NSNumber`` creation method.
176
177 Boxing a value of enum type will result in a ``NSNumber`` pointer with a
178 creation method according to the underlying type of the enum, which can
179 be a :ref:`fixed underlying type <objc-fixed-enum>`
180 or a compiler-defined integer type capable of representing the values of
181 all the members of the enumeration:
182
183 .. code-block:: objc
184
185     typedef enum : unsigned char { Red, Green, Blue } Color;
186     Color col = Red;
187     NSNumber *nsCol = @(col); // => [NSNumber numberWithUnsignedChar:]
188
189 Boxed C Strings
190 ---------------
191
192 A C string literal prefixed by the ``'@'`` token denotes an ``NSString``
193 literal in the same way a numeric literal prefixed by the ``'@'`` token
194 denotes an ``NSNumber`` literal. When the type of the parenthesized
195 expression is ``(char *)`` or ``(const char *)``, the result of the
196 boxed expression is a pointer to an ``NSString`` object containing
197 equivalent character data, which is assumed to be '\\0'-terminated and
198 UTF-8 encoded. The following example converts C-style command line
199 arguments into ``NSString`` objects.
200
201 .. code-block:: objc
202
203     // Partition command line arguments into positional and option arguments.
204     NSMutableArray *args = [NSMutableArray new];
205     NSMutableDictionary *options = [NSMutableDictionary new];
206     while (--argc) {
207         const char *arg = *++argv;
208         if (strncmp(arg, "--", 2) == 0) {
209             options[@(arg + 2)] = @(*++argv);   // --key value
210         } else {
211             [args addObject:@(arg)];            // positional argument
212         }
213     }
214
215 As with all C pointers, character pointer expressions can involve
216 arbitrary pointer arithmetic, therefore programmers must ensure that the
217 character data is valid. Passing ``NULL`` as the character pointer will
218 raise an exception at runtime. When possible, the compiler will reject
219 ``NULL`` character pointers used in boxed expressions.
220
221 Container Literals
222 ==================
223
224 Objective-C now supports a new expression syntax for creating immutable
225 array and dictionary container objects.
226
227 Examples
228 --------
229
230 Immutable array expression:
231
232 .. code-block:: objc
233
234     NSArray *array = @[ @"Hello", NSApp, [NSNumber numberWithInt:42] ];
235
236 This creates an ``NSArray`` with 3 elements. The comma-separated
237 sub-expressions of an array literal can be any Objective-C object
238 pointer typed expression.
239
240 Immutable dictionary expression:
241
242 .. code-block:: objc
243
244     NSDictionary *dictionary = @{
245         @"name" : NSUserName(),
246         @"date" : [NSDate date],
247         @"processInfo" : [NSProcessInfo processInfo]
248     };
249
250 This creates an ``NSDictionary`` with 3 key/value pairs. Value
251 sub-expressions of a dictionary literal must be Objective-C object
252 pointer typed, as in array literals. Key sub-expressions must be of an
253 Objective-C object pointer type that implements the
254 ``<NSCopying>`` protocol.
255
256 Discussion
257 ----------
258
259 Neither keys nor values can have the value ``nil`` in containers. If the
260 compiler can prove that a key or value is ``nil`` at compile time, then
261 a warning will be emitted. Otherwise, a runtime error will occur.
262
263 Using array and dictionary literals is safer than the variadic creation
264 forms commonly in use today. Array literal expressions expand to calls
265 to ``+[NSArray arrayWithObjects:count:]``, which validates that all
266 objects are non-``nil``. The variadic form,
267 ``+[NSArray arrayWithObjects:]`` uses ``nil`` as an argument list
268 terminator, which can lead to malformed array objects. Dictionary
269 literals are similarly created with
270 ``+[NSDictionary dictionaryWithObjects:forKeys:count:]`` which validates
271 all objects and keys, unlike
272 ``+[NSDictionary dictionaryWithObjectsAndKeys:]`` which also uses a
273 ``nil`` parameter as an argument list terminator.
274
275 Object Subscripting
276 ===================
277
278 Objective-C object pointer values can now be used with C's subscripting
279 operator.
280
281 Examples
282 --------
283
284 The following code demonstrates the use of object subscripting syntax
285 with ``NSMutableArray`` and ``NSMutableDictionary`` objects:
286
287 .. code-block:: objc
288
289     NSMutableArray *array = ...;
290     NSUInteger idx = ...;
291     id newObject = ...;
292     id oldObject = array[idx];
293     array[idx] = newObject;         // replace oldObject with newObject
294
295     NSMutableDictionary *dictionary = ...;
296     NSString *key = ...;
297     oldObject = dictionary[key];
298     dictionary[key] = newObject;    // replace oldObject with newObject
299
300 The next section explains how subscripting expressions map to accessor
301 methods.
302
303 Subscripting Methods
304 --------------------
305
306 Objective-C supports two kinds of subscript expressions: *array-style*
307 subscript expressions use integer typed subscripts; *dictionary-style*
308 subscript expressions use Objective-C object pointer typed subscripts.
309 Each type of subscript expression is mapped to a message send using a
310 predefined selector. The advantage of this design is flexibility: class
311 designers are free to introduce subscripting by declaring methods or by
312 adopting protocols. Moreover, because the method names are selected by
313 the type of the subscript, an object can be subscripted using both array
314 and dictionary styles.
315
316 Array-Style Subscripting
317 ^^^^^^^^^^^^^^^^^^^^^^^^
318
319 When the subscript operand has an integral type, the expression is
320 rewritten to use one of two different selectors, depending on whether
321 the element is being read or written. When an expression reads an
322 element using an integral index, as in the following example:
323
324 .. code-block:: objc
325
326     NSUInteger idx = ...;
327     id value = object[idx];
328
329 it is translated into a call to ``objectAtIndexedSubscript:``
330
331 .. code-block:: objc
332
333     id value = [object objectAtIndexedSubscript:idx];
334
335 When an expression writes an element using an integral index:
336
337 .. code-block:: objc
338
339     object[idx] = newValue;
340
341 it is translated to a call to ``setObject:atIndexedSubscript:``
342
343 .. code-block:: objc
344
345     [object setObject:newValue atIndexedSubscript:idx];
346
347 These message sends are then type-checked and performed just like
348 explicit message sends. The method used for objectAtIndexedSubscript:
349 must be declared with an argument of integral type and a return value of
350 some Objective-C object pointer type. The method used for
351 setObject:atIndexedSubscript: must be declared with its first argument
352 having some Objective-C pointer type and its second argument having
353 integral type.
354
355 The meaning of indexes is left up to the declaring class. The compiler
356 will coerce the index to the appropriate argument type of the method it
357 uses for type-checking. For an instance of ``NSArray``, reading an
358 element using an index outside the range ``[0, array.count)`` will raise
359 an exception. For an instance of ``NSMutableArray``, assigning to an
360 element using an index within this range will replace that element, but
361 assigning to an element using an index outside this range will raise an
362 exception; no syntax is provided for inserting, appending, or removing
363 elements for mutable arrays.
364
365 A class need not declare both methods in order to take advantage of this
366 language feature. For example, the class ``NSArray`` declares only
367 ``objectAtIndexedSubscript:``, so that assignments to elements will fail
368 to type-check; moreover, its subclass ``NSMutableArray`` declares
369 ``setObject:atIndexedSubscript:``.
370
371 Dictionary-Style Subscripting
372 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
373
374 When the subscript operand has an Objective-C object pointer type, the
375 expression is rewritten to use one of two different selectors, depending
376 on whether the element is being read from or written to. When an
377 expression reads an element using an Objective-C object pointer
378 subscript operand, as in the following example:
379
380 .. code-block:: objc
381
382     id key = ...;
383     id value = object[key];
384
385 it is translated into a call to the ``objectForKeyedSubscript:`` method:
386
387 .. code-block:: objc
388
389     id value = [object objectForKeyedSubscript:key];
390
391 When an expression writes an element using an Objective-C object pointer
392 subscript:
393
394 .. code-block:: objc
395
396     object[key] = newValue;
397
398 it is translated to a call to ``setObject:forKeyedSubscript:``
399
400 .. code-block:: objc
401
402     [object setObject:newValue forKeyedSubscript:key];
403
404 The behavior of ``setObject:forKeyedSubscript:`` is class-specific; but
405 in general it should replace an existing value if one is already
406 associated with a key, otherwise it should add a new value for the key.
407 No syntax is provided for removing elements from mutable dictionaries.
408
409 Discussion
410 ----------
411
412 An Objective-C subscript expression occurs when the base operand of the
413 C subscript operator has an Objective-C object pointer type. Since this
414 potentially collides with pointer arithmetic on the value, these
415 expressions are only supported under the modern Objective-C runtime,
416 which categorically forbids such arithmetic.
417
418 Currently, only subscripts of integral or Objective-C object pointer
419 type are supported. In C++, a class type can be used if it has a single
420 conversion function to an integral or Objective-C pointer type, in which
421 case that conversion is applied and analysis continues as appropriate.
422 Otherwise, the expression is ill-formed.
423
424 An Objective-C object subscript expression is always an l-value. If the
425 expression appears on the left-hand side of a simple assignment operator
426 (=), the element is written as described below. If the expression
427 appears on the left-hand side of a compound assignment operator (e.g.
428 +=), the program is ill-formed, because the result of reading an element
429 is always an Objective-C object pointer and no binary operators are
430 legal on such pointers. If the expression appears in any other position,
431 the element is read as described below. It is an error to take the
432 address of a subscript expression, or (in C++) to bind a reference to
433 it.
434
435 Programs can use object subscripting with Objective-C object pointers of
436 type ``id``. Normal dynamic message send rules apply; the compiler must
437 see *some* declaration of the subscripting methods, and will pick the
438 declaration seen first.
439
440 Caveats
441 =======
442
443 Objects created using the literal or boxed expression syntax are not
444 guaranteed to be uniqued by the runtime, but nor are they guaranteed to
445 be newly-allocated. As such, the result of performing direct comparisons
446 against the location of an object literal (using ``==``, ``!=``, ``<``,
447 ``<=``, ``>``, or ``>=``) is not well-defined. This is usually a simple
448 mistake in code that intended to call the ``isEqual:`` method (or the
449 ``compare:`` method).
450
451 This caveat applies to compile-time string literals as well.
452 Historically, string literals (using the ``@"..."`` syntax) have been
453 uniqued across translation units during linking. This is an
454 implementation detail of the compiler and should not be relied upon. If
455 you are using such code, please use global string constants instead
456 (``NSString * const MyConst = @"..."``) or use ``isEqual:``.
457
458 Grammar Additions
459 =================
460
461 To support the new syntax described above, the Objective-C
462 ``@``-expression grammar has the following new productions:
463
464 ::
465
466     objc-at-expression : '@' (string-literal | encode-literal | selector-literal | protocol-literal | object-literal)
467                        ;
468
469     object-literal : ('+' | '-')? numeric-constant
470                    | character-constant
471                    | boolean-constant
472                    | array-literal
473                    | dictionary-literal
474                    ;
475
476     boolean-constant : '__objc_yes' | '__objc_no' | 'true' | 'false'  /* boolean keywords. */
477                      ;
478
479     array-literal : '[' assignment-expression-list ']'
480                   ;
481
482     assignment-expression-list : assignment-expression (',' assignment-expression-list)?
483                                | /* empty */
484                                ;
485
486     dictionary-literal : '{' key-value-list '}'
487                        ;
488
489     key-value-list : key-value-pair (',' key-value-list)?
490                    | /* empty */
491                    ;
492
493     key-value-pair : assignment-expression ':' assignment-expression
494                    ;
495
496 Note: ``@true`` and ``@false`` are only supported in Objective-C++.
497
498 Availability Checks
499 ===================
500
501 Programs test for the new features by using clang's \_\_has\_feature
502 checks. Here are examples of their use:
503
504 .. code-block:: objc
505
506     #if __has_feature(objc_array_literals)
507         // new way.
508         NSArray *elements = @[ @"H", @"He", @"O", @"C" ];
509     #else
510         // old way (equivalent).
511         id objects[] = { @"H", @"He", @"O", @"C" };
512         NSArray *elements = [NSArray arrayWithObjects:objects count:4];
513     #endif
514
515     #if __has_feature(objc_dictionary_literals)
516         // new way.
517         NSDictionary *masses = @{ @"H" : @1.0078,  @"He" : @4.0026, @"O" : @15.9990, @"C" : @12.0096 };
518     #else
519         // old way (equivalent).
520         id keys[] = { @"H", @"He", @"O", @"C" };
521         id values[] = { [NSNumber numberWithDouble:1.0078], [NSNumber numberWithDouble:4.0026],
522                         [NSNumber numberWithDouble:15.9990], [NSNumber numberWithDouble:12.0096] };
523         NSDictionary *masses = [NSDictionary dictionaryWithObjects:objects forKeys:keys count:4];
524     #endif
525
526     #if __has_feature(objc_subscripting)
527         NSUInteger i, count = elements.count;
528         for (i = 0; i < count; ++i) {
529             NSString *element = elements[i];
530             NSNumber *mass = masses[element];
531             NSLog(@"the mass of %@ is %@", element, mass);
532         }
533     #else
534         NSUInteger i, count = [elements count];
535         for (i = 0; i < count; ++i) {
536             NSString *element = [elements objectAtIndex:i];
537             NSNumber *mass = [masses objectForKey:element];
538             NSLog(@"the mass of %@ is %@", element, mass);
539         }
540     #endif
541
542 Code can use also ``__has_feature(objc_bool)`` to check for the
543 availability of numeric literals support. This checks for the new
544 ``__objc_yes / __objc_no`` keywords, which enable the use of
545 ``@YES / @NO`` literals.
546
547 To check whether boxed expressions are supported, use
548 ``__has_feature(objc_boxed_expressions)`` feature macro.