what exactly constitutes a conditional statement in Objective C?
I've been reading the book Learn Objective C on the Mac, and I was looking at this bit of sample code:
#import <Foundation/Foundation.h>
int main (int argc, const char * argv[])
{
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
NSFileManager *manager;
manager = [NSFileManager defaultManager];
NSString *home;
home = [@"~" stringByExpandingTildeInPath];
NSDirectoryEnumerator *direnum;
direnum = [manager enumeratorAtPath: home];
NSMutableArray *files;
files = [NSMutableArray arrayWithCapacity: 42];
// “Slow” enumeration
NSString *filename;
while ( filename = [direnum nextObject] )
{
if ([[filename pathExtension] isEqualTo: @”jpg”])
{
[files addObject: filename];
} // end if
} // end while
NSEnumerator *filenum;
filenum = [files objectEnumerator];
while ( filename = [filenum nextObject] )
{
NSLog(@”%@”, filename);
}
[pool drain];
return 0;
} // main
what stood out for me was while ( filename = [filenum nextObject] )
and I thought, 'how this is 开发者_如何学编程actually a conditional statement?' I suppose a call to [filenum nextObject]
is an NSString with a filename, or nil, but how do we get to execute filename =
while we are evaluating that? can you point me to the correct documentation that would explain more clearly just what is possible here?
This is actually a feature of C. The while statement takes an expression like an if statement and an assignment is a valid expression. In this C grammar file you can see the following is valid
IF '(' expression ')' statement
and also
WHILE '(' expression ')' statement
As long as the result from the expression is non zero the condition will be true. A nil value is 0 and will cause the condition to fail. Once the enumerator is done nextObject will return nil and the condition will fail. It is however recommended when doing an assignment as a conditional expression you should surround it with parentheses to state your intentions.
while ( (filename = [direnum nextObject]) )
This is a conditional statement since every assignation has a value, which is the value on the right hand side assigned to the var on the left.
In this case, the final value turns out to be, either a valid NSString
object, or nil.
As long as nil
represents "nothing", the condition is interpreted as false, otherwise it's true.
while ( filename = [filenum nextObject] )
This statement is complex and performs multiple operations.
[filenum nextObject]
method is called and returns an NSStringfilename =
gets assigned the address of the NSString- the value of
filename
is evaluated as a condition for thewhile ( ... )
operation
As you pointed out if the returned value is nil
then filename equals nil
and the condition evaluates to false else filename is non-zero and the condition evaluates to true.
Many programers don't like this kind of syntax. It is terse and can be difficult to maintain. Compilers will generate a warning, to flag a common syntax error for when the developer actually intend to compare the two values,
while ( filename == [filenum nextObject] )
It would be cleaner to write the original statement as
while ( (filename = [filenum nextObject]) != nil )
This statement will behave the same as the original but eliminates the ambiguity of the assignment and the conditional operations.
You have raised a good question. Consider the code
while ( obj = [enumerator nextObject] ) {
printf( "%s\n", [[obj description] cString] );
}
The reason why while ( obj = [array objectEnumerator] )
works is because objectEnumerator returns nil on the last object. Since in C nil is usually 0, this is the same as false. ( ( obj = [array objectEnumerator] ) != nil )
might be preferable
Source : Click This Link !
In your case, ((filename = [direnum nextObject]) )
is another way of doing this to avoid compiler errors.
The expression
(file = [filenum nextObject])
Will be executed each time through the loop. After it is excecuted it is then evaluated as the Boolean condition for the if statement
It's the same as a normal statement like
x = 13 * 4;
Everything to the right of the equals is executed and then it is assigned to the variable x.
精彩评论