(sorry, this turned into a tome)

The way properties are compiled has changed over time. Assuming you're using 
the current (Xcode 4.6+) version of clang to compile your files, there is an 
explicit 'atomic' attribute for properties. This has been around for some time. 
(Keep in mind that out-of-date information never gets removed from 
StackOverflow. It's a treacherous place to use as your primary source of 
information.)

The purpose of the explicit 'atomic' keyword is so that you don't let 
atomic/nonatomic default. There is a companion compiler option in the build 
settings ("Implicit Atomic Objective-C Properties") which you can set to YES to 
get a warning when you don't specify either nonatomic or atomic.

The reason for this is not much about performance. ('atomic' is slower, but not 
by much.) It's more about what happens when you write custom accessors. For 
example

        @property id someProperty;

        - (void) setSomeProperty: (id) newValue {
                _someProperty = newValue;
        }

This is a bug, because you've declared "someProperty" atomic (by default), but 
you didn't provide an atomic implementation. Secondarily, in the above example, 
when there's no custom getter, the compiler will object that it can't 
synthesize the getter. If you declare the property nonatomic, the compiler will 
happily synthesize the getter for you.

At a different level, forcing yourself to specify nonatomic or atomic will help 
you to remember whether you need the property to be atomic or not. If you make 
it atomic, you are probably dealing with a thread synchronization issue. But in 
many cases making the property atomic does *not* produce thread safe code, and 
in many cases thread safe code doesn't need atomic properties. Properties that 
truly need to be atomic are rare in most apps.

The current paradigm for declaring properties is like this:

        @interface MyClass : …
        @property (nonatomic) id someProperty; // or 'atomic' if that's what 
you want.
        @end
        
        @implementation MyClass;
        @end

The implementation uses auto-synthesis, which does three things:

1.      It synthesizes the ivar that backs the property (with the name 
_someProperty, with a leading underscore).
2.      It synthesizes the getter.
3.      It synthesizes the setter.

Note that if you synthesize explicitly like this:

        @implementation MyClass;
        @synthesize someProperty;
        @end

the compiler does the same three things *except* that it synthesizes the ivar 
with the name someProperty, without a leading underscore.

If you want to declare a private ivar yourself, you should do it in the 
implementation and not in the interface:

        @implementation MyClass
        {
                NSNumber* _someProperty;
        }
        @end

If you're writing your own getter and/or setter, none of the above changes. 
Except for one thing. If you provide both a getter and a setter, the compiler 
does *not* auto-synthesize the ivar. You must either declare the ivar 
explicitly, as in the immediately preceding example, or with an explicit 
synthesize:

        @synthesize someProperty = _someProperty;

Be careful about whether the synthesize will put a leading underscore on the 
ivar name. Because the rules have been in transition, it's easy to end up with 
the wrong name, producing a hard-to-find bug.



_______________________________________________

Cocoa-dev mailing list (Cocoa-dev@lists.apple.com)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:
https://lists.apple.com/mailman/options/cocoa-dev/archive%40mail-archive.com

This email sent to arch...@mail-archive.com

Reply via email to