Become a MacRumors Supporter for $50/year with no ads, ability to filter front page stories, and private forums.

jamesapp

macrumors 6502a
Original poster
Mar 7, 2008
544
0
james-collinss-macbook-pro:prog15 jamescollins$ gcc -framework Foundation AddressBook.m prog15.11.m -o prog15.11
AddressBook.m: In function ‘-[AddressBook initWithName:]’:
AddressBook.m:8: warning: conflicting types for ‘-(id)initWithName:(NSString *)name’
AddressBook.h:11: warning: previous declaration of ‘-(AddressBook *)initWithName:(NSString *)name’
AddressBook.m: In function ‘-[AddressBook list]’:
AddressBook.m:34: warning: ‘cString’ is deprecated (declared at /System/Library/Frameworks/Foundation.framework/Headers/NSString.h:345)
AddressBook.m:39: warning: ‘cString’ is deprecated (declared at /System/Library/Frameworks/Foundation.framework/Headers/NSString.h:345)
AddressBook.m:40: warning: ‘cString’ is deprecated (declared at /System/Library/Frameworks/Foundation.framework/Headers/NSString.h:345)
AddressBook.m:48: error: ‘dealloc’ undeclared (first use in this function)
AddressBook.m:48: error: (Each undeclared identifier is reported only once
AddressBook.m:48: error: for each function it appears in.)
AddressBook.m:48: error: syntax error before ‘{’ token
AddressBook.m: At top level:
AddressBook.m:53: warning: incomplete implementation of class ‘AddressBook’
AddressBook.m:53: warning: method definition for ‘-dealloc’ not found

got these error messages when i tried to compile a program from a book on Objective-C.

-i was told cString is no longer used, so i understand that warning message.
the thing that i don't understand is AddressBook.m:48 error: 'dealloc' undeclared (first use in this function)...
i have in my interface file
Code:
-(void) dealloc;

i will include the interface file which i called AddressBook.h
Code:
#import <Foundation/NSArray.h>
#import <stdio.h>
#import "AddressCard.h"

@interface AddressBook: NSObject
{
  NSString       *bookName;
  NSMutableArray *book;
}

-(AddressBook *) initWithName: (NSString *) name;
-(void) addCard: (AddressCard *) theCard;
-(int) entries;
-(void) list;
-(void) dealloc;

@end

and my implementation file which i called AddressBook.m
Code:
#import "AddressBook.h"

@implementation AddressBook;

// set up the AddressBook's name and an empty book

-(id) initWithName: (NSString *) name
{
  self = [super init];
  if (self) {
    bookName = [[NSString alloc] initWithString: name];
    book = [[NSMutableArray alloc] init];
    }
    
  return self;
}

-(void) addCard: (AddressCard *) theCard
{
  [book addObject: theCard];
}

-(int) entries
{
  return [book count];
}

-(void) list
{
  int     i, elements;
  AddressCard *theCard;
  
  printf ("\n======== Contents of: %s =========\n",
           [bookName cString]);
  elements = [book count];
  
  for ( i = 0; i < elements; ++i ) {
      theCard = [book objectAtIndex: i];
      printf ("%-20s %-32s\n", [[theCard name] cString],
                   [[theCard email] cString]);
  }
  
  printf("========================================\
          ============\n\n");
  
          
-(void) dealloc
{
  [bookName release];
  [book release];
  [super dealloc];
}
@end

and my test file which i called prog15.11.m
Code:
#import "AddressBook.h"
#import <Foundation/NSAutoreleasePool.h>

int main (int argc, char *argv[])
{
  NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
  
  NSString *aName = @"Julia Kochan";
  NSString *aEmail = @"jewls337@axlc.com";
  NSString *bName = @"Tony Iannino";
  NSString *bEmail = @"tony.iannino@techfitness.com";
  NSString *cName = @"Stephen Kochan";
  NSString *cEmail = @"steve@kochan-wood.com";
  NSString *dName = @"Jamie Baker";
  NSString *dEmail = @"jbaker@kochan-wood.com";
  
  AddressCard *card1 = [[AddressCard alloc] init];
  AddressCard *card2 = [[AddressCard alloc] init];
  AddressCard *card3 = [[AddressCard alloc] init];
  AddressCard *card4 = [[AddressCard alloc] init];
  
  AddressBook *myBook = [AddressBook alloc];
  
  // first set up four address cards
  
  [card1 setName: aName andEmail: aEmail];
  [card2 setName: bName andEmail: bEmail];
  [card3 setName: cName andEmail: cEmail];
  [card4 setName: dName andEmail: dEmail];
  
  // now initialize the address book
  
  myBook = [myBook initWithName: @"Linda's Address Book"];
  
  printf ("Entries in address book after creation: %i\n",
              [myBook entries]);
              
  // Add some cards to the address book
  
  [myBook addCard: card1];
  [myBook addCard: card2];
  [myBook addCard: card3];
  [myBook addCard: card4];
  
  printf ("Entries in address book after adding cards: %i\n\n",
              [myBook entries]);
              
  // list all the entries in the book now
  
  [myBook list];
  
  [card1 release];
  [card2 release];
  [card3 release];
  [card4 release];
  [myBook release];
  [pool release];
  return 0;
}

didn't i declare dealloc in my interface file?
what is the syntax error before '{' token?
 

Nutter

macrumors 6502
Mar 31, 2005
432
0
London, England
You're only importing <Foundation/NSArray.h> in your header file. -(void)dealloc is declared <Foundation/NSObject.h>

I'd suggest that you change the import statement to the following:
#import <Foundation/Foundation.h>

This will include all the headers for the Foundation framework, including both NSObject.h and NSArray.h.

It isn't necessary to redeclare -(void)dealloc in your header file, as it's declared by the superclass, NSObject.

By the way, you can use -UTF8String instead of -cString.
 

Krevnik

macrumors 601
Sep 8, 2003
4,101
1,312
Another game of spot the bug. :)

The bug is here, at the end of the list method:

Code:
-(void) list
{
  int     i, elements;
  AddressCard *theCard;
  
  printf ("\n======== Contents of: %s =========\n",
           [bookName cString]);
  elements = [book count];
  
  for ( i = 0; i < elements; ++i ) {
      theCard = [book objectAtIndex: i];
      printf ("%-20s %-32s\n", [[theCard name] cString],
                   [[theCard email] cString]);
  }
  
  printf("========================================\
          ============\n\n");
  
          
-(void) dealloc
{
  [bookName release];
  [book release];
  [super dealloc];
}

If you look closely, the list method isn't closed off. This leads to the series of compile errors you see. Fix that, and the dealloc undeclared error should go away too.
 

jamesapp

macrumors 6502a
Original poster
Mar 7, 2008
544
0
where should i close off list.
i tried at the end of
Code:
AddressCard *theCard;
got more error messages
i closed off list with '}', is that what you meant
 

jamesapp

macrumors 6502a
Original poster
Mar 7, 2008
544
0
tried to put '}' right after printf and before dealloc
got following error messages when i tried to compile

james-collinss-macbook-pro:prog15 jamescollins$ gcc -framework Foundation AddressBook.m prog15.11.m -o prog15.11
AddressBook.m: In function ‘-[AddressBook initWithName:]’:
AddressBook.m:8: warning: conflicting types for ‘-(id)initWithName:(NSString *)name’
AddressBook.h:11: warning: previous declaration of ‘-(AddressBook *)initWithName:(NSString *)name’
Undefined symbols:
".objc_class_name_AddressCard", referenced from:
literal-pointer@__OBJC@__cls_refs@AddressCard in ccBDrI05.o
ld: symbol(s) not found
collect2: ld returned 1 exit status
 

iSee

macrumors 68040
Oct 25, 2004
3,540
272
It actually compiled, so now you're on to other bugs!

Here's the one causing the first warning:

in the header, initWithName returns an AddressBook pointer, while in the .m file it returns an id:
Header:
Code:
-(AddressBook *) initWithName: (NSString *) name;
.m file:
Code:
-(id) initWithName: (NSString *) name
 

kainjow

Moderator emeritus
Jun 15, 2000
7,958
7
Undefined symbols:
".objc_class_name_AddressCard", referenced from:
literal-pointer@__OBJC@__cls_refs@AddressCard in ccBDrI05.o
ld: symbol(s) not found
collect2: ld returned 1 exit status

Looks like you're not compiling AddressCard into your code. Try compiling like this:

Code:
gcc -framework Foundation [b]AddressCard.m[/b] AddressBook.m prog15.11.m -o prog15.11
 

Eraserhead

macrumors G4
Nov 3, 2005
10,434
12,250
UK
You also should put if blocks around the stuff you're releasing i.e.

Code:
if(bookName!=nil){
	[bookName release];
}
if(book!=nil){
	[book release];
}
 

Krevnik

macrumors 601
Sep 8, 2003
4,101
1,312
You also should put if blocks around the stuff you're releasing i.e.

Code:
if(bookName!=nil){
    [bookName release];
}
if(book!=nil){
    [book release];
}

I have been curious, how needed is that? In my experience, calling release on a nil object is usually safe(ish).
 

Krevnik

macrumors 601
Sep 8, 2003
4,101
1,312
You said it yourself. Safe(ish) is not safe :). Better be safe than sorry, I can imagine trying to debug a possible error relating from that to be rather stressful.

Well, the main reason I say safe-ish, is that I haven't seen a crash from calling release on a nil object... But yeah, defensive is usually better. :p
 

kainjow

Moderator emeritus
Jun 15, 2000
7,958
7
On the other hand if you're dealing with CoreFoundation types, you must check for NULL before releasing those when using CFRelease().
 

GeeYouEye

macrumors 68000
Dec 9, 2001
1,669
10
State of Denial
Nope, releasing nil in dealloc isn't just safe-ish, it's desired. Apple does it throughout Cocoa that way. There's a huge discussion of this very topic on Apple's Cocoa-dev mailing list. Go right ahead and get rid of those if's.
 

Krevnik

macrumors 601
Sep 8, 2003
4,101
1,312
Nope, releasing nil in dealloc isn't just safe-ish, it's desired. Apple does it throughout Cocoa that way. There's a huge discussion of this very topic on Apple's Cocoa-dev mailing list. Go right ahead and get rid of those if's.

Awesome, now I know all those [var release] lines in my older code weren't the result of some delusion. I was being productively lazy. :)
 

jamesapp

macrumors 6502a
Original poster
Mar 7, 2008
544
0
compiled with AddressCard.m and program compiled
still confused about
warning: conflicting types for ‘-(id)initWithName:(NSString *)name’
AddressBook.h:11: warning: previous declaration of ‘-(AddressBook *)initWithName:(NSString *)name’
 

kainjow

Moderator emeritus
Jun 15, 2000
7,958
7
Reread iSee's post. You need to keep the method declaration and implementation the same. They are different.
 
Register on MacRumors! This sidebar will go away, and you'll see fewer ads.