Simple Question

Discussion in 'Mac Programming' started by tooom, Sep 7, 2010.

  1. macrumors newbie

    Joined:
    Sep 7, 2010
    #1
    I'm starting with objective c. I wrote the following stuff but I do not understand what I'm doing wrong

    MyClass.h
    Code:
    #import <Cocoa/Cocoa.h>
    
    
    @interface MyClass : NSObject {}
    
    +(MyClass*) initMyClass;
    
    @end
    MyClass.m
    Code:
    #import "MyClass.h"
    
    @implementation MyClass
    
    +(MyClass*) initMyClass {
    	self = [super init];
    	return self;
    }
    
    @end
    And Prog1.m
    Code:
    #import <Foundation/NSObject.h> 
    #import <Foundation/NSAutoreleasePool.h> 
    #import <Foundation/NSString.h> 
    #import <Foundation/NSArray.h> 
    #import <Foundation/NSValue.h>
    #import <stdio.h>
    #import "MyClass.h"
    
    int main (int argc, const char * argv[]) {
        NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];
    	
    	printf("1\n");
    	MyClass* myClass = [MyClass initMyClass];
    	printf("2\n");
    	[myClass autorelease];
    	printf("3\n");
    	MyClass* myClass2 = myClass;
    	printf("4\n");
    	[myClass2 retain];
    	printf("5\n");
    	[myClass release];
    	printf("6\n");	
    	
    	
    	[pool release];
    	return 0;
    }
    There are some includes from XCode that are not necessary (i know). The program terminates and i do not understand why. I get the following error message on the console:
    Code:
    Program loaded.
    run
    [Switching to process 20067]
    Running…
    1
    2010-09-07 21:10:49.667 Prog1[20067:a0f] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '*** +[MyClass<0x100001080> init]: cannot init a class object.'
    *** Call stack at first throw:
    (
    	0   CoreFoundation                      0x00007fff83a27cc4 __exceptionPreprocess + 180
    	1   libobjc.A.dylib                     0x00007fff86ef70f3 objc_exception_throw + 45
    	2   CoreFoundation                      0x00007fff83a80f59 +[NSObject(NSObject) init] + 137
    	3   Prog1                               0x0000000100000e67 +[MyClass initMyClass] + 57
    	4   Prog1                               0x0000000100000d83 main + 103
    	5   Prog1                               0x0000000100000d14 start + 52
    	6   ???                                 0x0000000000000001 0x0 + 1
    )
    terminate called after throwing an instance of 'NSException'
    Program received signal:  “SIGABRT”.
    sharedlibrary apply-load-rules all

    What's wrong here? :confused:
     
  2. macrumors 68030

    Catfish_Man

    Joined:
    Sep 13, 2001
    Location:
    Portland, OR
    #2
    You're doing [MyClass initMyClass] instead of [[MyClass alloc] initMyClass]. You have to allocate space for an object before you can initialize it.

    <edit>
    Corollary: +initMyClass should be -initMyClass. An instance method, not a class method.
    </edit>
     
  3. macrumors 603

    Joined:
    Aug 9, 2009
    #3
    You're not telling us how you're starting with Objective-C.

    Are you following an online tutorial?
    Which one? Post its URL.

    Are you reading a book?
    Which one? Post its title and author.

    Are you haphazardly trying code from various places on the internet?
    Not a good idea. Almost any book or tutorial would be better.
     
  4. macrumors 68030

    jared_kipe

    Joined:
    Dec 8, 2003
    Location:
    Seattle
    #4
    I think some of the confusion is on the usage of + vs - methods. I remember when I first started, I thought a lot of things should be + that really shouldn't be.

    As stated before
    + methods can only be called on the class itself.
    In Cocoa these are almost always convenience methods that return fresh objects or singleton instances.

    For example, your class could be rewritten like this:
    Code:
    + (MyClass *) newMyClass {
         MyClass *newObject = [[MyClass alloc] init];
         return [newObject autorelease];
    }
    
    Another example would be if you were writing a class to provide some math functionality..

    Code:
    + (double) sin: (double) x {
         // some sin() implementation
    }
    
    This method could be a class method because it doesn't require an instance to do its work. (It obviously could be a C function instead of a class method.)
     
  5. macrumors 68000

    Sydde

    Joined:
    Aug 17, 2009
    #5
    Hey there, oops: should you be using autorelease in a method that has "new" in the name? I mean, just for consistency sake.
     
  6. thread starter macrumors newbie

    Joined:
    Sep 7, 2010
    #6
    Okay, thanks for the answers. I've modified my code in the following way
    Code:
    int main (int argc, const char * argv[]) {
        NSAutoreleasePool* pool = [[NSAutoreleasePool alloc] init];
    	
    	printf("1\n");
    	MyClass* myClass = [[MyClass alloc] initMyClass];
    	printf("2\n");
    	[myClass autorelease];
    	printf("3\n");
    	MyClass* myClass2 = myClass;
    	printf("4\n");
    	[myClass2 retain];
    	printf("5\n");
    	[myClass release];
    	printf("6\n");	
    	
    	
    	[pool release];
    	return 0;
    }
    Now, it runs. But I'm wondering if the object myClass has been added to the autoreleasepool?
     
  7. macrumors 68030

    Catfish_Man

    Joined:
    Sep 13, 2001
    Location:
    Portland, OR
    #7
    Yes. Calling -autorelease on an object adds it to the topmost autorelease pool.
     
  8. macrumors 68030

    jared_kipe

    Joined:
    Dec 8, 2003
    Location:
    Seattle
    #8
    Generally yes. Since the method itself doesn't need to retain ownership. The caller should retain any object that it creates, and it is almost always assumed that the incoming object is autoreleased.
     

Share This Page