/ / Objective C project
- Open Xcode and create a new project

- Select Command Line Utility under the Mac OS icon on the left
- In the right panel select Foundation Tool
, then press Choose.
Save the project as Hello

- Click on your_file.m file. You should see the following:
#import <Foundation/Foundation.h>
int main (int argc, const char * argv[]) {
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
// insert code here...
NSLog(@"Hello, World!");
[pool drain];
return 0;
}
Delete everything and type in the following:
#import <Foundation/Foundation.h>
int main (int argc, const char * argv[]) {
NSLog(@"Hello, World!");
return 0;
}
- Build and run (⌘+R) will compile and run the program, but instead press ⌘+⇧+R to compile and run the program in the console window.
Breaking it down
Extensions
The
.m extension gets processed by the Objective-C compiler.
The
.c extension gets processed by the C compiler.
The
.cpp extension gets processed by the C++ compiler.
The convention is to refer to the .m files as "dot-m files"
#import
In C one uses #include to tell the compiler to look at a certain file for some definitions.
In Objective-C, use #import. #import guarantees that the header file will be included only once.
The Foundation framework is about 1 megabyte. It contains more than 14,000 lines of code and is comprised of
hundreds of files.
NSLog() and @"strings"
NSLog() prints a string to the Console. The method takes a string as its first argument and can contain
format specifiers like %d or %f. NSLog() not only prints your string to the console, but it adds a time and date stamp and appends a newline(\n) character at the end of the line.
What is NS all about
The NS prefix is from when the toolkit was called NextSTEP and was a product of NeXT Software. NeXT was bought by
Apple in 1996 and instead of rewriting all the code, Apple continued to use the NS prefix.
A string in double quotes preceded by the @ sign means that the quoted string should be treated as a NSString element.
NSString can:
- Tell you its length
- Compare itself to a string
- Convert itself to an integer or floating-point value
/ / Indirection
Write a program that opens a file and prints out the length of each word in file
- Open BBEdit and create a list of words. Your words can also be phases, but separate each item by a newline.
Save the file as words in your work folder.
- Open Terminal and type cd, then drag the words.txt file into the window. You should now see a path to your file that you will need to place in your code.
- Open Xcode and create a new project

- Select Command Line Utility under the Mac OS icon on the left
- In the right panel select Foundation Tool
, then press Choose.
Save the project as Length_of_word

- Click on your_file.m file. You should see the following:
#import <Foundation/Foundation.h>
int main (int argc, const char * argv[]) {
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
// insert code here...
NSLog(@"Hello, World!");
[pool drain];
return 0;
}
Delete everything and type in the following:
#import <Foundation/Foundation.h>
int main (int argc, const char * argv[]) {
FILE *wordFile=fopen("your_path_to_file","r");
char word[100];
while(fgets(word,100,wordFile)){
word[strlen(word)-1]='\0';
NSLog(@"%s is %d characters long",word,strlen(word));
}
fclose(wordFile);
return 0;
return 0;
}
- Build and run (⌘+R) will compile and run the program, but instead press ⌘+⇧+R to compile and run the program in the console window.
This is a good example of indirection. Rather than coding the words directly into the program, you have your program get the words from the text file.
- Change the above code to :
#import <Foundation/Foundation.h>
int main (int argc, const char * argv[]) {
if(argc==1){
NSLog(@"you need to provide a file name");
}
FILE *wordFile=fopen(argv[1],"r");
char word[100];
while(fgets(word,100,wordFile)){
word[strlen(word)-1]='\0';
NSLog(@"%s is %d characters long",word,strlen(word));
}
fclose(wordFile);
return 0;
}
- Expand Executables
- Double-click on the name of the program
- Click on the plus sign in the Arguments section and type the launch argument, in this case the path to your words.txt.
- Run
- Now try this file: /usr/share/dict/words
/ / Inheritance
When you have several classes that all share common interfaces and implementations,
inheritance can eliminate the redundancy and simplify your code.
Unlike other OOP languages, Objective-C does not support multiple inheritance.
@interface Shape:NSObject{
ShapeColor fillColor;
ShapeRect bounds;
}
-(void) setFillColor: (ShapeColor) fillColor;
-(void) setBounds: (ShapeRect) bounds;
-(void) draw;
@end//Rectangle
@implementation Shape
-(void) setFillColor:(ShapeColor) c{
fillColor=c;
}
-(void) setBounds: (ShapeRect) b{
bounds=b;
}
-(void) draw {
}
@end//Shape
@interface Circle: Shape
@end//Circle
@implementation Circle
-(void) draw {
NSLog(@"drawing a rectangle at (%d %d %d %d) in %@",
bounds.x,bounds.y, bounds.with, bounds.height, colorName(fillColor));
}
@end//
@interface Rectangle: Shape
@end//Rectangle
@implementation Rectangle
-(void) draw {
NSLog(@"drawing a rectangle at (%d %d %d %d) in %@",
bounds.x,bounds.y, bounds.with, bounds.height, colorName(fillColor));
}
@end//Rectangle
Notice that both Circle and Rectangle @interface do not have cury braces.
If you don't have instance variables, you don't have curly braces.
Simplifying your code is known as
refactoring.
When you refactor, you move code around to improve the architecture
(eliminating duplicate code) without
changing the code's behavior or results.
In the example above:
The superclass is of Circle is Shape.
The Parent class of Shape is NSObject.
A subclass of Shape is Rectangle
A Child class of Shape is Circle
The draw method in Rectangle and Circle overrides the draw method in Shape.
/ / Overriding methods
When you make your own subclasses, you often create your own methods. Sometimes you add a method that creates
a unique feature to your class. Sometimes, you want to enhance an existing method from your superclass.
Obj-C provides a way to override a method and still call the superclass's implementaion. T call the inherited method implementation, you use
super as the target for a method call.
What do you think is happening here:
@implementation Circle
-(void) setFillColor: (ShapeColor) c{
if(c==kRedColor){
c=kGreenColor;
}
[super setFillColor:c];
}
-(void) draw {
NSLog(@"drawing a rectangle at (%d %d %d %d) in %@",
bounds.x,bounds.y, bounds.with, bounds.height, colorName(fillColor));
}
@end//
When you override a ethod, invoking the superclass is almost always a good idea. This way you can be assured that you get all the features
the super method implements.
Create a program that has subclasses.