CodeToLive

Foundation Framework in Objective-C

The Foundation framework provides fundamental classes and data types for Objective-C development, including strings, collections, dates, and more.

Foundation Framework is a core Objective-C framework that provides basic utility classes and data types used across all Apple platforms.

Basic Data Types

NSString and NSMutableString


// String creation
NSString *immutableStr = @"Hello World";
NSString *formattedStr = [NSString stringWithFormat:@"Value: %d", 42];

// Mutable string
NSMutableString *mutableStr = [NSMutableString stringWithString:@"Hello"];
[mutableStr appendString:@" World"];

// Common operations
NSUInteger length = [immutableStr length];
NSString *substring = [immutableStr substringToIndex:5];
NSRange range = [immutableStr rangeOfString:@"World"];
            

NSNumber


// Number creation
NSNumber *intNum = @42;                  // Literal syntax
NSNumber *floatNum = @3.14f;             // Float
NSNumber *boolNum = @YES;                // Boolean

// Converting back to primitives
int intValue = [intNum intValue];
float floatValue = [floatNum floatValue];
BOOL boolValue = [boolNum boolValue];
            

Collections

NSArray and NSMutableArray


// Immutable array
NSArray *immutableArray = @[@"One", @"Two", @"Three"];

// Mutable array
NSMutableArray *mutableArray = [NSMutableArray arrayWithArray:immutableArray];
[mutableArray addObject:@"Four"];

// Fast enumeration
for (NSString *item in immutableArray) {
    NSLog(@"%@", item);
}

// Common operations
NSUInteger count = [immutableArray count];
NSString *first = [immutableArray firstObject];
BOOL contains = [immutableArray containsObject:@"Two"];
            

NSDictionary and NSMutableDictionary


// Immutable dictionary
NSDictionary *immutableDict = @{@"key1": @"value1", @"key2": @"value2"};

// Mutable dictionary
NSMutableDictionary *mutableDict = [NSMutableDictionary dictionaryWithDictionary:immutableDict];
[mutableDict setObject:@"value3" forKey:@"key3"];

// Accessing values
NSString *value = immutableDict[@"key1"];  // Modern syntax
NSString *oldValue = [immutableDict objectForKey:@"key2"];  // Traditional

// Enumerating
[immutableDict enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
    NSLog(@"Key: %@, Value: %@", key, obj);
}];
            

NSSet and NSMutableSet


// Set creation (unordered, unique objects)
NSSet *immutableSet = [NSSet setWithObjects:@"A", @"B", @"C", nil];
NSMutableSet *mutableSet = [NSMutableSet setWithSet:immutableSet];

// Operations
[mutableSet addObject:@"D"];
[mutableSet removeObject:@"B"];
BOOL contains = [immutableSet containsObject:@"A"];

// Set operations
NSSet *otherSet = [NSSet setWithObjects:@"B", @"C", @"D", nil];
NSSet *unionSet = [immutableSet setByAddingObjectsFromSet:otherSet];
NSSet *intersect = [immutableSet objectsPassingTest:^BOOL(id obj, BOOL *stop) {
    return [otherSet containsObject:obj];
}];
            

Dates and Time


// Current date
NSDate *now = [NSDate date];

// Date from components
NSDateComponents *comps = [[NSDateComponents alloc] init];
[comps setDay:10];
[comps setMonth:10];
[comps setYear:2010];
NSCalendar *gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian];
NSDate *date = [gregorian dateFromComponents:comps];

// Date formatting
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
NSString *dateStr = [formatter stringFromDate:now];

// Date calculations
NSDate *yesterday = [now dateByAddingTimeInterval:-86400];
NSTimeInterval secondsBetween = [now timeIntervalSinceDate:yesterday];
            

File System Operations


// File manager
NSFileManager *fileManager = [NSFileManager defaultManager];

// Path utilities
NSString *documentsPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) firstObject];
NSString *filePath = [documentsPath stringByAppendingPathComponent:@"data.txt"];

// File operations
BOOL exists = [fileManager fileExistsAtPath:filePath];
if (!exists) {
    [@"Hello World" writeToFile:filePath atomically:YES encoding:NSUTF8StringEncoding error:nil];
}

// Reading data
NSString *fileContents = [NSString stringWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:nil];

// Directory listing
NSArray *files = [fileManager contentsOfDirectoryAtPath:documentsPath error:nil];
            

Networking


// URL handling
NSURL *url = [NSURL URLWithString:@"https://api.example.com/data"];
NSURLRequest *request = [NSURLRequest requestWithURL:url];

// URLSession data task
NSURLSessionDataTask *task = [[NSURLSession sharedSession] dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
    if (error) {
        NSLog(@"Error: %@", error);
        return;
    }
    
    NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)response;
    if (httpResponse.statusCode == 200) {
        NSError *jsonError;
        NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:0 error:&jsonError];
        if (!jsonError) {
            NSLog(@"Received JSON: %@", json);
        }
    }
}];
[task resume];
            

Key-Value Coding (KVC)


@interface Person : NSObject
@property (nonatomic, copy) NSString *name;
@property (nonatomic) NSInteger age;
@end

// Using KVC
Person *person = [[Person alloc] init];
[person setValue:@"John" forKey:@"name"];
[person setValue:@30 forKey:@"age"];

NSString *name = [person valueForKey:@"name"];
NSInteger age = [[person valueForKey:@"age"] integerValue];

// Key paths
NSArray *people = @[person1, person2, person3];
NSArray *names = [people valueForKeyPath:@"name"];
NSNumber *avgAge = [people valueForKeyPath:@"@avg.age"];
            

Key-Value Observing (KVO)


// Adding observer
[person addObserver:self 
         forKeyPath:@"age" 
            options:NSKeyValueObservingOptionNew | NSKeyValueObservingOptionOld 
            context:nil];

// Implementing observer method
- (void)observeValueForKeyPath:(NSString *)keyPath 
                      ofObject:(id)object 
                        change:(NSDictionary *)change 
                       context:(void *)context {
    if ([keyPath isEqualToString:@"age"]) {
        NSNumber *oldAge = change[NSKeyValueChangeOldKey];
        NSNumber *newAge = change[NSKeyValueChangeNewKey];
        NSLog(@"Age changed from %@ to %@", oldAge, newAge);
    }
}

// Remember to remove observer
- (void)dealloc {
    [person removeObserver:self forKeyPath:@"age"];
}
            

Notifications


// Posting a notification
[[NSNotificationCenter defaultCenter] postNotificationName:@"DataUpdated" object:self];

// Observing a notification
[[NSNotificationCenter defaultCenter] addObserver:self 
                                        selector:@selector(handleDataUpdated:) 
                                            name:@"DataUpdated" 
                                          object:nil];

// Handling notification
- (void)handleDataUpdated:(NSNotification *)notification {
    NSLog(@"Data was updated by: %@", notification.object);
}

// Removing observer
- (void)dealloc {
    [[NSNotificationCenter defaultCenter] removeObserver:self];
}
            

Best Practices

Note: Many Foundation classes have toll-free bridging with their Core Foundation counterparts (e.g., NSString ↔ CFStringRef).

Next: Cocoa & Cocoa Touch in Objective-C