Re: Implementing NSFastEnumeration

Gerd Knops <[email protected]>
Newsgroups gmane.comp.macosx.devel
Message-ID <[email protected]>
On Oct 1, 2009, at 8:13 AM, Christiaan Hofman wrote:

> I've been reading the documentation on NSFastEnumeration (both the  
> docs on the protocol and the section in the Objective-C 2.0  
> Programming Language guide). But it is really cryptic and misses  
> most of the relevant information to help in implementing it.

Below some code I have been using. To access the array to be  
enumerated, it uses these methods that my code provides:

- (unsigned)version;
- (unsigned)countOfChildrenAtVersion:(unsigned)aVersion;
- (id)childAtIndex:(unsigned)index forVersion:(unsigned)aVersion;

It makes use of the extra array to keep track of the version it is  
enumerating, in case it changes while the enumeration goes on. In my  
case it is safe to use "self" as the mutationsPtr because the only way  
the child array might change is by adding additional children.

Looking at it now I am not sure if the [child retain] part is correct,  
might create a memory leak. I'll have to check on that. And it'll need  
some changes to be 64-bit safe.

But anyway this should get you started.

Gerd

- (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *) 
state
	objects:(id *)stackbuf
	count:(NSUInteger)len
{
	
	// typedef struct {
	//    unsigned long state;
	//    id *itemsPtr;
	//    unsigned long *mutationsPtr;
	//    unsigned long extra[5];
	// } NSFastEnumerationState;
	
	unsigned	idx=state->state;
	unsigned	version=(idx>0)?state->extra[0]:[self version];
	unsigned	numChildren=[self countOfChildrenAtVersion:version];
	NSUInteger	now=0;
	
	while(now<len && idx<numChildren)
	{
		id	child=[self childAtIndex:idx forVersion:version];
		
		stackbuf[now++]=[child retain];
		idx++;
	}
	
	state->extra[0]=version;
	state->state=(unsigned long)idx;
	state->itemsPtr=stackbuf;
	state->mutationsPtr=(unsigned long *)self;
	
	return now;
}
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.