Discussion:
Objective-C: Hiding Methods
(too old to reply)
Jaeson Engle
1998-04-20 04:38:03 UTC
Permalink
I'm very new to Objective-C, and am looking for something that I can't
seem to find in the PB online docs or any other source of Objective-C
documentation. What I would like to do is define some methods for a
class I'm writing which are not accessable from the outside of the
class @implementation section. The problem I'm seeing is that I can't
send a message to self for a method which is not defined in the
@interface section. So the question is really two-fold: 1) can I send a
message within the class without using self, and 2) if not, is there
any way to this kind of implementation hiding?

Many thanks,
Jaeson


--
Jaeson Engle - Programmer At Large
<mailto:***@tundra.org>
<http://www.engle.org/>
Finger for PGP Public Block
"Macsbug is not a screensaver."
Andrew Abernathy
1998-04-20 06:43:37 UTC
Permalink
Post by Jaeson Engle
What I would like to do is define some methods for a
class I'm writing which are not accessable from the outside of the
You can't really do this. I'm guessing that you really want to define
some methods for use within your class, but which you don't want to
advertise. The convention for doing this is to declare the extra
methods in a category in the implementation file. For example:


MyClass.h:

@interface MyClass : NSObject
{
int bleep;
}

- (void)setBleep:(int)newBleep;
- (int)bleep;

@end


MyClass.m:

@interface MyClass (Private)

- (void)blah;

@end


@implementation MyClass

- (void)setBleep:(int)newBleep; { bleep = newBleep; }
- (int)bleep; { return bleep; }
- (void)blah; { NSLog (@"blah here"; }

@end

---
***@omnigroup.com - MIME mail ok
Tomi Engel
1998-04-20 09:19:26 UTC
Permalink
Post by Jaeson Engle
I'm very new to Objective-C, and am looking for something that I can't
seem to find in the PB online docs or any other source of Objective-C
documentation. What I would like to do is define some methods for a
class I'm writing which are not accessable from the outside of the
send a message to self for a method which is not defined in the
@interface section. So the question is really two-fold: 1) can I send a
message within the class without using self, and 2) if not, is there
any way to this kind of implementation hiding?
Many thanks,
Jaeson
While Objective C has a notion of public, private and protected ivars
there is no similar formal conzept for methods.
However...since ObjcC builds on top of C and it all comes down to
pointers and regular funciton call even the ivar classification is just a
"compiler-warning" trigger and no real security feature.

So you can reach the same level of "privacy" for methods with two
different approaches:

1. Define a category which contains the private methods and put it into a
headerfile which is not made available (public) if your classes are
shared within the project or placed in a framework. This is a normal
approach which is used by Apple as well. It would look like this

@interface MyClass(PrivateMethods)

- (void)_updateCache;
- (id)_funkyResult;

@end

It is an unspoken convention that those methods are marked with an
underscore so that even people who poke around in your app/framework know
that they are dealing with "evil-private" methods.
However...there is no (obviouse or trivial) way to ensure that only self
is using those methods, unless your wirte your own runtime functions.

2 To really make a "method" private you could use a local function. Since
private usually means "not accessible by subclasses as well" there is no
reason for making this a real dispatchable, polymorphic function (method).
If you need a protected method then this does not work and you are stuck
with approach nr. 1.




Aloha
Tomi
Timothy J. Wood
1998-04-20 09:42:36 UTC
Permalink
From: Jaeson Engle <<***@tundra.org>

Subject: Objective-C: Hiding Methods

[...]
Post by Jaeson Engle
What I would like to do is define some methods for a
class I'm writing which are not accessable from the outside of the
[...]



Typically how you do this is to have two headers Foo.h and FooPrivate.h like so:


-- Foo.h --

#import <<Foundation/NSObject.h>


@interface Foo : NSObject

{

}


- (void) publicMethod1;

- (void) publicMethod2;


@end


-- FooPrivate.h --

#import "Foo.h"


@interface Foo (PrivateAPI)


- (void) privateMethod1;

- (void) privateMethod2;


@end


-- Foo.m --

#import "Foo.h"

#import "FooPrivate.h"


@implementation Foo


- (void) publicMethod1;

{

}


- (void) publicMethod2;

{

}


@end



@implementation Foo (PrivateAPI)


- (void) privateMethod1;

{

}


- (void) privateMethod2;

{

}


@end
Ross Tulloch
1998-04-20 12:07:36 UTC
Permalink
Post by Tomi Engel
While Objective C has a notion of public, private and protected ivars
there is no similar formal conzept for methods.
How about adding this ability to the Objective C language? Sounds like
something a good OO language should have.

Who exactly controls the ObjC language these days?
Is it still being developed?


Ross.
Mont Rothstein
1998-04-20 21:31:16 UTC
Permalink
Post by Ross Tulloch
Post by Tomi Engel
While Objective C has a notion of public, private and protected ivars
there is no similar formal conzept for methods.
How about adding this ability to the Objective C language? Sounds like
something a good OO language should have.
Who exactly controls the ObjC language these days?
Is it still being developed?
Ross.
Apple controls it. NeXT bought the rights from StepStone.

In general with a mature language like ObjC, I'm usually against changing it.
Obviously infant languages like Java still need to grow and evolve, but this
is painful (witness all the Java 1.x.x upgrade problems) and should be
stopped as soon as possible.

It is very hard to develop when your tools are a moving target. Note: this
is also true for libraries, and the port to OpenStep and EOF 2.x were
painful, but the predecesors will still immature and needed to be evolved.

-Mont
MIke Laster
1998-04-21 02:00:48 UTC
Permalink
Post by Mont Rothstein
In general with a mature language like ObjC, I'm usually against changing it.
Obviously infant languages like Java still need to grow and evolve, but this
is painful (witness all the Java 1.x.x upgrade problems) and should be
stopped as soon as possible.
It is very hard to develop when your tools are a moving target. Note: this
is also true for libraries, and the port to OpenStep and EOF 2.x were
painful, but the predecesors will still immature and needed to be evolved.
A moving target is definitely a bad thing, but is stagnation any better? There
are many things Objective-C could use. Top of my wish list is REAL exception
handling instead of those macro hacks. I would love to have something like
Java's 'finally' clause to handle cleanup after exceptions.
Mont Rothstein
1998-04-21 02:14:57 UTC
Permalink
Post by MIke Laster
A moving target is definitely a bad thing, but is stagnation any better?
There
are many things Objective-C could use. Top of my wish list is REAL exception
handling instead of those macro hacks. I would love to have something like
Java's 'finally' clause to handle cleanup after exceptions.
This is a tough one for me, because in general in life I am for change.
Change is good. If I look for examples in this industry I can see ANSI 'C'
on one side and Java on the other. Now you can say that 'C' did change and
get rev'd, the new revs are called C++ and Obj-C. And in a certain light
this is true, but we still have ANSI 'C', it is not obsolete, and I never
even have to think about it changing. If you look at all of the standards
bodies that Sun submitted Java to, ANSI wasn't on the list. They would have
laughed at the submission of something so young and unproven.

I think maybe the is an important lesson in C++ and Obj-C. First, both were
created after 'C' had been around for awhile. Second they gave a very clear
distinction between the old ('C') and the new (C++/Obj-C) so that everyone
could make a clear conscious decision about when/if they wanted to move. And
both C++ and Obj-C support ANSI 'C' (well actually Obj-C does, and C++ almost
does). Things become very muddied when you go through '.' revs, and each rev
does not have to be certified by a standards body.

Maybe the correct thing to do would be to create an Obj-C2 (or some other
name). Of course, before that is done someone (Apple) really ought to submit
Obj-C to ANSI (I could swear that when NeXT bought Obj-C they said they were
going to do this).

-Mont
s***@easynet.fr
1998-04-21 18:21:11 UTC
Permalink
Hi,
Post by MIke Laster
A moving target is definitely a bad thing, but is stagnation any better?
There
are many things Objective-C could use. Top of my wish list is REAL exception
handling instead of those macro hacks. I would love to have something like
Java's 'finally' clause to handle cleanup after exceptions.
Sure, true exceptions would be a good thing. Code-in-protocol
would be great to. A garbage collector would be nice. C++
declare-variables-anywhere would also be nice. Smalltalk cascaded
messages would be very usefull, now that most methods don't return self
anymore. Block objects would be nice, too.

But, as pointed by Mont, the wisest change for ObjC now, would be to
submit Obj-C to ANSI.

And, well, adding @protected methods would IMHO be a step backward. It
doesn't give any more functionnality. What would be the next step
? @friend :-) ? @primitive, to formalize primitive methods in class
clusters ? @designated-initializer to formalize designated initializers ?

Obj-C is a very simple langage with many conventions. I don't think
that formalizing the conventions would do any good to the core langage,
as we'll end up with a complex langage with many conventions. Or maybe
I'm wrong...

And maybe we should kill this thread...

Cheers

--fred
Kenneth C. Dyke
1998-04-21 18:08:41 UTC
Permalink
Date: Mon, 20 Apr 1998 19:02:18 -0700 (PDT)
Subject: Re: Objective-C: Hiding Methods
X-Listprocessor-Version: 6.0 -- ListProcessor by Anastasios Kotsikonas
X-Comment: To unsubscribe, follow directions at
http://www.omnigroup.com/MailArchive/
X-Mailer: Mozilla 4.05 (Macintosh; I; PPC)
A moving target is definitely a bad thing, but is stagnation any better?
There are many things Objective-C could use. Top of my wish list is REAL
exception handling instead of those macro hacks.
What would 'real' exception handling buy you with Objective C? They seem
sort of moot, IMHO, since GNU Objective C doesn't support statically
allocated objects (let alone the runtime that Apple is using). Thus, the
compiler really has no idea what objects should be destroyed (if any) when an
execption is thrown.

Call me sick and demented, but I actually LIKE the fact that the current
exception model keeps itself out of the compiler and is handled as a runtime
issue. I'd prefer to keep as much of the 'magic' in the runtime system as
possible, rather than add more complexity to the compiler.

What I do is just make sure that when an exception is thrown, any objects
that should have been blown away are sitting in an autorelease pool, either
directly or via some kind of object graph. If I make it out of the code
without an exception being thrown, the object graph is retained, and the
release method sent when the pool is destroyed is "harmless".

-Kenneth
Timothy J. Wood
1998-04-21 18:30:20 UTC
Permalink
From: "Kenneth C. Dyke" <<***@jumpgate.com>

Subject: "Real" ObjC Exception handling? (was Re: Objective-C: Hiding Methods)

[...]
Post by Kenneth C. Dyke
What would 'real' exception handling buy you with Objective C? They seem
sort of moot, IMHO, since GNU Objective C doesn't support statically
allocated objects (let alone the runtime that Apple is using). Thus, the
compiler really has no idea what objects should be destroyed (if any) when an
execption is thrown.
There are couple cool things that could be done. First off, if the
support from the new egcs compiler were moved into ObjC, you would have
zero-cost exception handler setup/removal. Right now there is a tradeoff
between trapping exceptions in the low layers of your code and getting
smacked with big performance penalties due to the setup overhead. This is
especially true in multi-threaded code since the exception handler stack
is per-thread. With builtin thread support, symbols can be injected into
a ".eh" segment that, given the PC of each frame can be used to determine
at raise/catch time what handlers are appropriate for that function.


<nofill>
Post by Kenneth C. Dyke
Call me sick and demented, but I actually LIKE the fact that the current
exception model keeps itself out of the compiler and is handled as a runtime
issue. I'd prefer to keep as much of the 'magic' in the runtime system as
possible, rather than add more complexity to the compiler.
</nofill>

Yeah, this is true, but in the case of exceptions, they could be much
more useful and cheap (therefor, actually used more, making life easier
for all involved) if they were supported by the compiler.

<nofill>
Post by Kenneth C. Dyke
What I do is just make sure that when an exception is thrown, any objects
that should have been blown away are sitting in an autorelease pool, either
directly or via some kind of object graph. If I make it out of the code
without an exception being thrown, the object graph is retained, and the
release method sent when the pool is destroyed is "harmless".
</nofill>

First off, we really need the support for naming the possible set of
returned exceptions from a method/function that Java has.


As a generalized example of what you suggest above, there really needs
to be a way of tagging methods as allocating resources and other methods
as releasing resources. This would apply not only to object allocation
but to opening files, connecting sockets, aquiring locks or otherwise
getting access to some scarce system resource that would be leaked if an
exception were raised. This is really quite a hard problem though. :)


-tim

Douglas Davidson
1998-04-20 18:19:20 UTC
Permalink
There are several things to remember here. The first is that
Objective-C is not a straitjacket. There is hardly a restriction in
the language that cannot be circumvented if you know what you are
doing (in which case you probably also know why you shouldn't do it).
Good behavior is enforced primarily by convention.

In particular, there is no way that you can hide an Objective-C
method entirely from a determined investigator. The runtime must
know about all methods, and it will divulge this information to
anyone who asks. If someone knows a method's name and signature,
then they can send it to an object. Declarations of methods in
@interface sections are purely to inform the compiler; the real work
is all done dynamically at runtime.

That said, the conventions for this particular issue are as follows:

- If you wish your class and some of its methods to be available to
anyone who links against your executable, define them in a public
header file (check the 'Public Header' box in ProjectBuilder's File
Attributes inspector)

- If you wish certain classes or methods to be available only within
the scope of your project, define them in a separate header file
(often with the word 'Private' in its name) and do not make it a
public header file. If the header file is in a subproject and needs
to be available to other subprojects, check the 'Project Header' box;
if only its own subproject should see it, do not. Remember that a
single class can have many @interface sections; the one that defines
the ivars will be the main section, and all of the others will be
categories.

- If you wish certain classes or methods to be available only within
the scope of a single source file, then define them in an @interface
section at the start of the .m file. This is the best practice, but
even this is not absolutely necessary--the compiler will not
complain about the use of an un-prototyped method, as long as it has
already seen its definition somewhere earlier in the file. If you
are really sloppy, you can neglect even this, and simply ignore the
compiler warnings (except that you may run into problems if some of
your arguments or return values are not 4 bytes long).

- In addition, methods that are meant to be implementation-internal
by convention have their names prefixed with an underscore. This
puts anyone else who might be tempted to use such a method on notice
that they do so at their own risk.

- If you really wish to hide functionality, you can use a function
rather than a method, in addition to all of the preceding practices.

I find it best to think of the notion of 'internal' in this context
as meaning 'internal to a set of source that is maintained together',
not necessarily as having any relationship to class boundaries. It
is quite possible to define a method internally to MySource.m that is
in a category on some class defined in somebody else's framework;
contrariwise, it is more common than not for a well-designed class to
have a well-defined, public API for subclassing.

Douglas Davidson
Software Quality
MIke Laster
1998-04-21 02:00:02 UTC
Permalink
Post by Douglas Davidson
- If you wish your class and some of its methods to be available to
anyone who links against your executable, define them in a public
header file (check the 'Public Header' box in ProjectBuilder's File
Attributes inspector)
- If you wish certain classes or methods to be available only within
the scope of your project, define them in a separate header file
(often with the word 'Private' in its name) and do not make it a
public header file. If the header file is in a subproject and needs
to be available to other subprojects, check the 'Project Header' box;
if only its own subproject should see it, do not. Remember that a
the ivars will be the main section, and all of the others will be
categories.
Unfortuately, this doesn't adequately cover the notion of protected methods.
If you place them in the public interface, then they may be called by outside
objects. If you don't place them in the public interface, programmers won't
know it is available to subclass off of. Objective-C could use an @protected
clause. Actually, the @private, @public don't work in the method declaration
section, so it could use them all.
Continue reading on narkive:
Loading...