Scope in an interface?

  • I am coming from the c++ world and I feel I don't understand how
    objects are scoped in obj-c.

    What is the scope of m_controller (a c++ class) below?  The debugger
    shows m_controller as {...} with no other information. Other than that
    it seems to run fine.

    Can I think of an @interface as something similar to a c++ class?

    Also, is there some reading for people familiar with c++ trying to
    grok obj-c other than the apple dev docs?  (something quick and dirty)

    // simple.h

    #include "controller.hpp"

    @interface simple : NSView
    {
        @private
            controller m_controller;
    }

    - (void) initialize_something;
    - (void) drawRect: (NSRect) rect;

    @end

    // simple.mm

    - (void) initialize_something
    {
        m_controller.initialize_something();
    }

    - (void) drawRect: (NSRect) rect
    {
        NSLog(@"drawRect");
        m_controller.do_something();
    }
  • On Sun, May 25, 2008 at 12:29 AM, Graham Reitz <grahamreitz...> wrote:
    > Can I think of an @interface as something similar to a c++ class?

    A class in Obj-C consists of an interface and an implementation (you
    forgot the @implementation/@end in your example). Just like a class in
    C++ (usually) consists of the definition in the header and the
    function implementations in the cpp/cxx/C file.
  • Sorry, assume the @implementation/@end are there.  It's not an example
    meant to compile.

    It sounds like what I listed can be considered synonymous with a c++
    class?

    thanks,
    -graham

    On May 25, 2008, at 12:36 AM, stephen joseph butler wrote:

    > On Sun, May 25, 2008 at 12:29 AM, Graham Reitz <grahamreitz...>
    > wrote:
    >> Can I think of an @interface as something similar to a c++ class?
    >
    > A class in Obj-C consists of an interface and an implementation (you
    > forgot the @implementation/@end in your example). Just like a class in
    > C++ (usually) consists of the definition in the header and the
    > function implementations in the cpp/cxx/C file.
  • On May 25, 2008, at 12:29 AM, Graham Reitz wrote:

    > Also, is there some reading for people familiar with c++ trying to
    > grok obj-c other than the apple dev docs?  (something quick and
    > dirty)

    A bit of googling turned up this: http://ktd.club.fr/programmation/fichiers/cpp-objc-en.pdf

    Cheers,
    Ken
  • On 24 May '08, at 10:29 PM, Graham Reitz wrote:

    > Can I think of an @interface as something similar to a c++ class?

    Yes. @interface is a class declaration, just as 'class' is in C++. The
    variables declared in the "{...}" block are member variables, and are
    protected by default. The object models of the two languages are quite
    different, though, so classes and methods have differences in
    behavior...

    * The method implementations have to go inside a corresponding
    @implementation block.

    * No multiple inheritance, except of 'protocols', which you can think
    of as special class declarations with no member variables and only
    pure abstract virtual functions. (This is just like Java, which in
    fact got it from Obj-C.)

    * All methods are virtual.

    * RTTI on steroids. Just about all information about any class can be
    examined at runtime, and selectors are much more general than C++
    method pointers. (It's actually C++ that's the odd language out; most
    OOP languages have lots of reflection.)

    * No abstract methods (except in the special case of protocols.) If
    you want a method to be abstract you have to to do it by convention,
    documenting the method as abstract and putting in an implementation
    that does nothing or raises an exception.

    * No such thing as private or protected methods. (Since the runtime
    allows method calls to be generated at runtime using things like -
    performSelector:, there's no practical way to enforce this.) The usual
    equivalent is to use a 'category' to put the class's private
    declarations into a separate header file that clients aren't supposed
    to include.

    * Class methods (the ones that start with "+" instead of "-") are
    superficially like C++ static methods, but actually more powerful.
    They're actually instance methods of the class itself (the class is an
    object.) The most important difference is that they can be overridden
    by subclasses just like instance methods.

    * "Categories" allow classes to be extended after the fact. In effect,
    anyone can add new methods to any existing class. (For example, my app
    uses SHA-1 digests a lot, so I added a new -digest method to NSData
    that computes its digest.)

    * No stack-based (auto) objects. They have to be allocated on the
    heap, as with "new".

    * New objects are automatically zero-filled (as though operator new
    were using calloc.)

    * No notion of constructors or destructors built into the language.
    There's merely a (very strong, universal) convention of using an -init
    method for initialization; and the refcounting implementation in
    NSObject makes sure to call -dealloc before freeing the object.

    * No operator overloading. No polymorphic methods (overloading based
    on different parameter types). No optional parameters or default values.

    * Calling any method on a NULL object pointer doesn't crash, and
    doesn't call any code; instead, it's a no-op. This is actually
    extremely useful and can be taken advantage of to make your code much
    more concise by eliminating a lot of pointer checks.

    * The built-in type "id" is similar to "void*" but specific to object
    types. Any type of object can be assigned to or from "id" without
    needing a type-cast. (It's like the kind of unchecked dynamic typing
    used in languages like Python and Ruby.) Coming from C++ or Java this
    may seem nasty, but it helps smooth out many of the sharp edges caused
    by type-checking, especially in generic collection classes, without
    the complexity of C++ templates or the kind of type-inference found in
    functional languages.

    * Method dispatch is more dynamic; it's based on the name of the
    method (the selector) not a vtable offset. This means that even if you
    don't know the class of an object at compile time, you can still call
    methods on it. For example, given a declaration "id foo", you can call
    [foo doSomething] and it will successfully call a method named
    doSomething, if foo has a base class that implements it, no matter
    what the class hierarchy looks like.

    * No "fragile base class problem" for methods: you can add methods to
    a base class without breaking binary compatibility of subclasses. (The
    32-bit runtime has fragile instance variables, though, but the new 64-
    bit one doesn't.)

    Hope this helps :)

    —Jens
  • Outstanding!  Thanks Jens!

    Did you just type that up now?  That seems like a lot of effort.

    Much appreciated,
    -graham

    On May 25, 2008, at 2:41 AM, Jens Alfke wrote:

    >
    > On 24 May '08, at 10:29 PM, Graham Reitz wrote:
    >
    >> Can I think of an @interface as something similar to a c++ class?
    >
    > Yes. @interface is a class declaration, just as 'class' is in C++.
    > The variables declared in the "{...}" block are member variables,
    > and are protected by default. The object models of the two languages
    > are quite different, though, so classes and methods have differences
    > in behavior...
    >
    > * The method implementations have to go inside a corresponding
    > @implementation block.
    >
    > * No multiple inheritance, except of 'protocols', which you can
    > think of as special class declarations with no member variables and
    > only pure abstract virtual functions. (This is just like Java, which
    > in fact got it from Obj-C.)
    >
    > * All methods are virtual.
    >
    > * RTTI on steroids. Just about all information about any class can
    > be examined at runtime, and selectors are much more general than C++
    > method pointers. (It's actually C++ that's the odd language out;
    > most OOP languages have lots of reflection.)
    >
    > * No abstract methods (except in the special case of protocols.) If
    > you want a method to be abstract you have to to do it by convention,
    > documenting the method as abstract and putting in an implementation
    > that does nothing or raises an exception.
    >
    > * No such thing as private or protected methods. (Since the runtime
    > allows method calls to be generated at runtime using things like -
    > performSelector:, there's no practical way to enforce this.) The
    > usual equivalent is to use a 'category' to put the class's private
    > declarations into a separate header file that clients aren't
    > supposed to include.
    >
    > * Class methods (the ones that start with "+" instead of "-") are
    > superficially like C++ static methods, but actually more powerful.
    > They're actually instance methods of the class itself (the class is
    > an object.) The most important difference is that they can be
    > overridden by subclasses just like instance methods.
    >
    > * "Categories" allow classes to be extended after the fact. In
    > effect, anyone can add new methods to any existing class. (For
    > example, my app uses SHA-1 digests a lot, so I added a new -digest
    > method to NSData that computes its digest.)
    >
    > * No stack-based (auto) objects. They have to be allocated on the
    > heap, as with "new".
    >
    > * New objects are automatically zero-filled (as though operator new
    > were using calloc.)
    >
    > * No notion of constructors or destructors built into the language.
    > There's merely a (very strong, universal) convention of using an -
    > init method for initialization; and the refcounting implementation
    > in NSObject makes sure to call -dealloc before freeing the object.
    >
    > * No operator overloading. No polymorphic methods (overloading based
    > on different parameter types). No optional parameters or default
    > values.
    >
    > * Calling any method on a NULL object pointer doesn't crash, and
    > doesn't call any code; instead, it's a no-op. This is actually
    > extremely useful and can be taken advantage of to make your code
    > much more concise by eliminating a lot of pointer checks.
    >
    > * The built-in type "id" is similar to "void*" but specific to
    > object types. Any type of object can be assigned to or from "id"
    > without needing a type-cast. (It's like the kind of unchecked
    > dynamic typing used in languages like Python and Ruby.) Coming from C
    > ++ or Java this may seem nasty, but it helps smooth out many of the
    > sharp edges caused by type-checking, especially in generic
    > collection classes, without the complexity of C++ templates or the
    > kind of type-inference found in functional languages.
    >
    > * Method dispatch is more dynamic; it's based on the name of the
    > method (the selector) not a vtable offset. This means that even if
    > you don't know the class of an object at compile time, you can still
    > call methods on it. For example, given a declaration "id foo", you
    > can call [foo doSomething] and it will successfully call a method
    > named doSomething, if foo has a base class that implements it, no
    > matter what the class hierarchy looks like.
    >
    > * No "fragile base class problem" for methods: you can add methods
    > to a base class without breaking binary compatibility of subclasses.
    > (The 32-bit runtime has fragile instance variables, though, but the
    > new 64-bit one doesn't.)
    >
    > Hope this helps :)
    >
    > —Jens
  • On 25 May '08, at 1:53 PM, Graham Reitz wrote:

    > Did you just type that up now?  That seems like a lot of effort.

    Yeah, I typed it in last night. I have a strong interest in languages
    & runtimes, so it doesn't take a lot to get me started! Also, I
    strongly suspect the barista at Starbucks, earlier that evening,
    didn't hear that I asked for decaf... :-P

    —Jens
  • Am 25.05.2008 um 09:41 schrieb Jens Alfke:
    > * Calling any method on a NULL object pointer doesn't crash, and
    > doesn't call any code; instead, it's a no-op. This is actually
    > extremely useful and can be taken advantage of to make your code
    > much more concise by eliminating a lot of pointer checks.

    One warning: For methods that have a return value, only certain return
    types are supported (which will in that case return 0). So read up on
    the details if you want to send a message to NIL.

    > * Method dispatch is more dynamic; it's based on the name of the
    > method (the selector) not a vtable offset. This means that even if
    > you don't know the class of an object at compile time, you can still
    > call methods on it. For example, given a declaration "id foo", you
    > can call [foo doSomething] and it will successfully call a method
    > named doSomething, if foo has a base class that implements it, no
    > matter what the class hierarchy looks like.

    This is why ObjC supports "duck typing". Great tool in the tool belt.

    Cheers,
    -- Uli Kusterer
    "The Witnesses of TeachText are everywhere..."
    http://www.zathras.de
previous month may 2008 next month
MTWTFSS
      1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31  
Go to today