ObjFW  Check-in [42060f220c]

Overview
Comment:Add -[filtered{Array,Dictionary}UsingBlock].
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA3-256: 42060f220c11f7d855bf24c76209ca7940046f3a22679ba1386f2f108283be76
User & Date: js on 2010-12-12 00:38:53
Other Links: manifest | tags
Context
2010-12-12
01:21
Add -[mapped{Array,Dictionary}UsingBlock:]. check-in: 90c26dded5 user: js tags: trunk
00:38
Add -[filtered{Array,Dictionary}UsingBlock]. check-in: 42060f220c user: js tags: trunk
2010-12-11
20:27
Rename a few exception-related methods. check-in: 5e44debc07 user: js tags: trunk
Changes

Modified src/OFArray.h from [515c92c63e] to [1b937822bd].

16
17
18
19
20
21
22

23
24
25
26
27
28
29
#import "OFEnumerator.h"

@class OFDataArray;
@class OFString;

#ifdef OF_HAVE_BLOCKS
typedef void (^of_array_enumeration_block_t)(id obj, size_t idx, BOOL *stop);

#endif

/**
 * \brief A class for storing objects in an array.
 */
@interface OFArray: OFObject <OFCopying, OFMutableCopying, OFCollection,
    OFFastEnumeration>







>







16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
#import "OFEnumerator.h"

@class OFDataArray;
@class OFString;

#ifdef OF_HAVE_BLOCKS
typedef void (^of_array_enumeration_block_t)(id obj, size_t idx, BOOL *stop);
typedef BOOL (^of_array_filter_block_t)(id odj, size_t idx);
#endif

/**
 * \brief A class for storing objects in an array.
 */
@interface OFArray: OFObject <OFCopying, OFMutableCopying, OFCollection,
    OFFastEnumeration>
201
202
203
204
205
206
207










208
209
210
211
212
213
214
#ifdef OF_HAVE_BLOCKS
/**
 * Executes a block for each object.
 *
 * \param block The block to execute for each object
 */
- (void)enumerateObjectsUsingBlock: (of_array_enumeration_block_t)block;










#endif
@end

@interface OFArrayEnumerator: OFEnumerator
{
	OFDataArray   *array;
	size_t	      count;







>
>
>
>
>
>
>
>
>
>







202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
#ifdef OF_HAVE_BLOCKS
/**
 * Executes a block for each object.
 *
 * \param block The block to execute for each object
 */
- (void)enumerateObjectsUsingBlock: (of_array_enumeration_block_t)block;

/**
 * Returns a new array, only containing the objects for which the block returns
 * YES.
 *
 * \param block A block which determines if the object should be in the new
 *		array
 * \return A new, autoreleased OFArray
 */
- (OFArray*)filteredArrayUsingBlock: (of_array_filter_block_t)block;
#endif
@end

@interface OFArrayEnumerator: OFEnumerator
{
	OFDataArray   *array;
	size_t	      count;

Modified src/OFArray.m from [a3c50697c4] to [654b3f415b].

398
399
400
401
402
403
404





















405
406
407
408
409
410
411
	id *objs = [array cArray];
	size_t i, count = [array count];
	BOOL stop = NO;

	for (i = 0; i < count && !stop; i++)
		block(objs[i], i, &stop);
}





















#endif

- (void)dealloc
{
	id *objs = [array cArray];
	size_t i, count = [array count];








>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
	id *objs = [array cArray];
	size_t i, count = [array count];
	BOOL stop = NO;

	for (i = 0; i < count && !stop; i++)
		block(objs[i], i, &stop);
}

- (OFArray*)filteredArrayUsingBlock: (of_array_filter_block_t)block
{
	size_t count = [array count];
	id *tmp = [self allocMemoryForNItems: count
				    withSize: sizeof(id)];

	@try {
		id *objs = [array cArray];
		size_t i, j = 0;

		for (i = 0; i < count; i++)
			if (block(objs[i], i))
				tmp[j++] = objs[i];

		return [OFArray arrayWithCArray: tmp
					 length: j];
	} @finally {
		[self freeMemory: tmp];
	}
}
#endif

- (void)dealloc
{
	id *objs = [array cArray];
	size_t i, count = [array count];

Modified src/OFDictionary.h from [7714034657] to [03c29285b1].

15
16
17
18
19
20
21

22
23
24
25
26
27
28
#import "OFCollection.h"
#import "OFEnumerator.h"

@class OFArray;

#ifdef OF_HAVE_BLOCKS
typedef void (^of_dictionary_enumeration_block_t)(id key, id obj, BOOL *stop);

#endif

struct of_dictionary_bucket
{
	id <OFCopying> key;
	id object;
	uint32_t hash;







>







15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
#import "OFCollection.h"
#import "OFEnumerator.h"

@class OFArray;

#ifdef OF_HAVE_BLOCKS
typedef void (^of_dictionary_enumeration_block_t)(id key, id obj, BOOL *stop);
typedef BOOL (^of_dictionary_filter_block_t)(id key, id obj);
#endif

struct of_dictionary_bucket
{
	id <OFCopying> key;
	id object;
	uint32_t hash;
160
161
162
163
164
165
166











167
168
169
170
171
172
173
/**
 * Executes a block for each key / object pair.
 *
 * \param block The block to execute for each key / object pair.
 */
- (void)enumerateKeysAndObjectsUsingBlock:
    (of_dictionary_enumeration_block_t)block;











#endif
@end

@interface OFDictionaryEnumerator: OFEnumerator
{
	struct of_dictionary_bucket **data;
	uint32_t size;







>
>
>
>
>
>
>
>
>
>
>







161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
/**
 * Executes a block for each key / object pair.
 *
 * \param block The block to execute for each key / object pair.
 */
- (void)enumerateKeysAndObjectsUsingBlock:
    (of_dictionary_enumeration_block_t)block;

/**
 * Returns a new dictionary, only containing the objects for which the block
 * returns YES.
 *
 * \param block A block which determines if the object should be in the new
 *		dictionary
 * \return A new, autoreleased OFDictionary
 */
- (OFDictionary*)filteredDictionaryUsingBlock:
    (of_dictionary_filter_block_t)block;
#endif
@end

@interface OFDictionaryEnumerator: OFEnumerator
{
	struct of_dictionary_bucket **data;
	uint32_t size;

Modified src/OFDictionary.m from [172aac0082] to [971d7fc20d].

570
571
572
573
574
575
576















577
578
579
580
581
582
583
	size_t i;
	BOOL stop = NO;

	for (i = 0; i < size && !stop; i++)
		if (data[i] != NULL && data[i] != DELETED)
			block(data[i]->key, data[i]->object, &stop);
}















#endif

- (void)dealloc
{
	uint32_t i;

	for (i = 0; i < size; i++) {







>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
	size_t i;
	BOOL stop = NO;

	for (i = 0; i < size && !stop; i++)
		if (data[i] != NULL && data[i] != DELETED)
			block(data[i]->key, data[i]->object, &stop);
}

- (OFDictionary*)filteredDictionaryUsingBlock:
    (of_dictionary_filter_block_t)block
{
	OFMutableDictionary *dict = [OFMutableDictionary dictionary];
	size_t i;

	for (i = 0; i < size; i++)
		if (data[i] != NULL && data[i] != DELETED)
			if (block(data[i]->key, data[i]->object))
				[dict setObject: data[i]->object
					 forKey: data[i]->key];

	return dict;
}
#endif

- (void)dealloc
{
	uint32_t i;

	for (i = 0; i < size; i++) {

Modified tests/OFArrayTests.m from [c0fcdd0b1e] to [07eb64f276].

244
245
246
247
248
249
250




251
252
253
254
255
256
257
		case 0:
			return @"foo";
		case 1:
			return @"bar";
		}

		return nil;




	    }]) && [[m[0] objectAtIndex: 0] isEqual: @"foo"] &&
	    [[m[0] objectAtIndex: 1] isEqual: @"bar"])
#endif

	[pool drain];
}
@end







>
>
>
>
|
|





244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
		case 0:
			return @"foo";
		case 1:
			return @"bar";
		}

		return nil;
		}]) && [[m[0] description] isEqual: @"(foo, bar)"])

	TEST(@"-[filteredArrayUsingBlock:]",
	   [[[m[0] filteredArrayUsingBlock: ^ BOOL (id obj, size_t idx) {
		return ([obj isEqual: @"foo"] ? YES : NO);
	    }] description] isEqual: @"(foo)"])
#endif

	[pool drain];
}
@end

Modified tests/OFDictionaryTests.m from [65e2a63075] to [5becf67107].

139
140
141
142
143
144
145





146
147
148
149
150
151
152
			return @"value_1";
		if ([key isEqual: keys[1]])
			return @"value_2";

		return nil;
	    }]) && [[dict objectForKey: keys[0]] isEqual: @"value_1"] &&
	    [[dict objectForKey: keys[1]] isEqual: @"value_2"])





#endif

	TEST(@"-[count]", [dict count] == 2)

	TEST(@"+[dictionaryWithKeysAndObjects:]",
	    (dict = [OFDictionary dictionaryWithKeysAndObjects: @"foo", @"bar",
								@"baz", @"qux",







>
>
>
>
>







139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
			return @"value_1";
		if ([key isEqual: keys[1]])
			return @"value_2";

		return nil;
	    }]) && [[dict objectForKey: keys[0]] isEqual: @"value_1"] &&
	    [[dict objectForKey: keys[1]] isEqual: @"value_2"])

	TEST(@"-[filteredDictionaryUsingBlock:]",
	    [[[dict filteredDictionaryUsingBlock: ^ BOOL (id key, id obj) {
		return ([key isEqual: keys[0]] ?  YES : NO);
	    }] description] isEqual: @"{key1 = value_1}"])
#endif

	TEST(@"-[count]", [dict count] == 2)

	TEST(@"+[dictionaryWithKeysAndObjects:]",
	    (dict = [OFDictionary dictionaryWithKeysAndObjects: @"foo", @"bar",
								@"baz", @"qux",