Skip to content

Commit

Permalink
first commit
Browse files Browse the repository at this point in the history
  • Loading branch information
kevinlawler committed Feb 29, 2012
0 parents commit bfa104a
Show file tree
Hide file tree
Showing 3 changed files with 137 additions and 0 deletions.
8 changes: 8 additions & 0 deletions NSSingleton.h
@@ -0,0 +1,8 @@
//Subclassible thread-safe ARC singleton
//Copyright Kevin Lawler. Released under ISC.

@interface NSSingleton : NSObject
+(id) instance;
+(id) sharedInstance; //alias for instance
+(id) singleton; //alias for instance
@end
61 changes: 61 additions & 0 deletions NSSingleton.m
@@ -0,0 +1,61 @@
//Subclassible thread-safe ARC singleton
//Copyright Kevin Lawler. Released under ISC.

#import "NSSingleton.h"

@implementation NSSingleton

static NSMutableDictionary* _children;

+(void) initialize //thread-safe
{
if(!_children) {
_children = [[NSMutableDictionary alloc] init];
}

[_children setObject:[[self alloc] init] forKey:NSStringFromClass([self class])];
}

+(id) alloc {
id c;
if((c = [self instance])) {
return c;
}
return [self allocWithZone:nil];
}

-(id) init {
id c;
if((c = [_children objectForKey:NSStringFromClass([self class])])) { //sic, unfactored
return c;
}
self = [super init];
return self;
}

+(id) instance {
return [_children objectForKey:NSStringFromClass([self class])];
}

+(id) sharedInstance { //alias for instance
return [self instance];
}

+(id) singleton { //alias for instance
return [self instance];
}

//stop other creative stuff
+(id) new {
return [self alloc];
}

+(id)copyWithZone:(NSZone *)zone {
return [self instance];
}

+(id)mutableCopyWithZone:(NSZone *)zone {
return [self instance];
}

@end
68 changes: 68 additions & 0 deletions README.md
@@ -0,0 +1,68 @@
## Description

This is a singleton class for iOS, Objective-C, Cocoa Touch, iPhone, iPad. We offer no judgement as to whether or not to use singletons. If you do use singletons in your project, then use NSSingleton. NSSingleton is named in a manner designed to minimize the amount of discussion about singletons, pro or con.

NSSingleton is:

1. Subclassible (to the n-th degree)
2. ARC compatible
3. Thread-safe (uses +initialize, not @synchronize)
4. Macro-free
5. Swizzle-free
6. Simple

It has been tested only with ARC. This implementation chooses "not lazy" instead of "requires explicit initialization" or "locks to allocate".

## Use

1. Add the files to your project
2. Import the header using `#import "NSSingleton.h"`
3. Subclass the NSSingleton class in the following way:

<pre>
@interface MYSubclass : NSSingleton
</pre>

You may then retrieve the unique, ready-to-use instance of your class by calling any of the following methods:

<pre>
[MYSubclass instance]
[MYSubclass sharedInstance] //alias
[MYSubclass singleton] //alias
[[MYSubclass alloc] init] //bad style, but safe to call any number of times
</pre>

## Future Directions

1. This has been tested on ARC only. Test on projects without ARC support.
2. See if there are any meaningful differences with the swizzle method.
3. Macro the options to become lazy and either "require initialization" or "lock to allocate"

## License

Released under ISC (similar to 2-clause BSD)

## Testing / Verification

<pre>
@interface NSAlpha : NSSingleton
@end
@interface NSBravo : NSSingleton
@end
@interface NSCharlie : NSBravo
@end

@implementation NSAlpha
@end
@implementation NSBravo
@end
@implementation NSCharlie
@end

id a,b,c,d;
NSLog(@"%d=%d=%d", a=[NSSingleton instance], [[NSSingleton alloc] init], [[NSSingleton alloc] init]);
NSLog(@"%d=%d=%d", b=[NSAlpha instance], [[NSAlpha alloc] init], [[NSAlpha alloc] init]);
NSLog(@"%d=%d=%d", c=[NSBravo instance], [[NSBravo alloc] init], [[NSBravo alloc] init]);
NSLog(@"%d=%d=%d", d=[NSCharlie instance], [[NSCharlie alloc] init], [[NSCharlie alloc] init]);
NSLog(@"%d != %d != %d != %d", a, b, c, d);
</pre>

0 comments on commit bfa104a

Please sign in to comment.