1// Protocol Buffers - Google's data interchange format 2// Copyright 2015 Google Inc. All rights reserved. 3// https://developers.google.com/protocol-buffers/ 4// 5// Redistribution and use in source and binary forms, with or without 6// modification, are permitted provided that the following conditions are 7// met: 8// 9// * Redistributions of source code must retain the above copyright 10// notice, this list of conditions and the following disclaimer. 11// * Redistributions in binary form must reproduce the above 12// copyright notice, this list of conditions and the following disclaimer 13// in the documentation and/or other materials provided with the 14// distribution. 15// * Neither the name of Google Inc. nor the names of its 16// contributors may be used to endorse or promote products derived from 17// this software without specific prior written permission. 18// 19// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 20// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 21// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 22// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 23// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 24// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 25// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 26// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 27// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 28// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 29// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 31#import <Foundation/Foundation.h> 32#import <XCTest/XCTest.h> 33 34#import "GPBDictionary.h" 35 36#import "GPBTestUtilities.h" 37#import "google/protobuf/UnittestRuntimeProto2.pbobjc.h" 38 39// Pull in the macros (using an external file because expanding all tests 40// in a single file makes a file that is failing to work with within Xcode. 41//%PDDM-IMPORT-DEFINES GPBDictionaryTests.pddm 42 43//%PDDM-EXPAND TESTS_FOR_POD_VALUES(String, NSString, *, Objects, @"foo", @"bar", @"baz", @"mumble") 44// This block of code is generated, do not edit it directly. 45 46// To let the testing macros work, add some extra methods to simplify things. 47@interface GPBStringEnumDictionary (TestingTweak) 48- (instancetype)initWithEnums:(const int32_t [])values 49 forKeys:(const NSString * [])keys 50 count:(NSUInteger)count; 51@end 52 53static BOOL TestingEnum_IsValidValue(int32_t value) { 54 switch (value) { 55 case 700: 56 case 701: 57 case 702: 58 case 703: 59 return YES; 60 default: 61 return NO; 62 } 63} 64 65@implementation GPBStringEnumDictionary (TestingTweak) 66- (instancetype)initWithEnums:(const int32_t [])values 67 forKeys:(const NSString * [])keys 68 count:(NSUInteger)count { 69 return [self initWithValidationFunction:TestingEnum_IsValidValue 70 rawValues:values 71 forKeys:keys 72 count:count]; 73} 74@end 75 76 77#pragma mark - String -> UInt32 78 79@interface GPBStringUInt32DictionaryTests : XCTestCase 80@end 81 82@implementation GPBStringUInt32DictionaryTests 83 84- (void)testEmpty { 85 GPBStringUInt32Dictionary *dict = [[GPBStringUInt32Dictionary alloc] init]; 86 XCTAssertNotNil(dict); 87 XCTAssertEqual(dict.count, 0U); 88 XCTAssertFalse([dict getUInt32:NULL forKey:@"foo"]); 89 [dict enumerateKeysAndUInt32sUsingBlock:^(NSString *aKey, uint32_t aValue, BOOL *stop) { 90 #pragma unused(aKey, aValue, stop) 91 XCTFail(@"Shouldn't get here!"); 92 }]; 93 [dict release]; 94} 95 96- (void)testOne { 97 GPBStringUInt32Dictionary *dict = [[GPBStringUInt32Dictionary alloc] init]; 98 [dict setUInt32:100U forKey:@"foo"]; 99 XCTAssertNotNil(dict); 100 XCTAssertEqual(dict.count, 1U); 101 uint32_t value; 102 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 103 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 104 XCTAssertEqual(value, 100U); 105 XCTAssertFalse([dict getUInt32:NULL forKey:@"bar"]); 106 [dict enumerateKeysAndUInt32sUsingBlock:^(NSString *aKey, uint32_t aValue, BOOL *stop) { 107 XCTAssertEqualObjects(aKey, @"foo"); 108 XCTAssertEqual(aValue, 100U); 109 XCTAssertNotEqual(stop, NULL); 110 }]; 111 [dict release]; 112} 113 114- (void)testBasics { 115 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 116 const uint32_t kValues[] = { 100U, 101U, 102U }; 117 GPBStringUInt32Dictionary *dict = 118 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues 119 forKeys:kKeys 120 count:GPBARRAYSIZE(kValues)]; 121 XCTAssertNotNil(dict); 122 XCTAssertEqual(dict.count, 3U); 123 uint32_t value; 124 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 125 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 126 XCTAssertEqual(value, 100U); 127 XCTAssertTrue([dict getUInt32:NULL forKey:@"bar"]); 128 XCTAssertTrue([dict getUInt32:&value forKey:@"bar"]); 129 XCTAssertEqual(value, 101U); 130 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 131 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 132 XCTAssertEqual(value, 102U); 133 XCTAssertFalse([dict getUInt32:NULL forKey:@"mumble"]); 134 135 __block NSUInteger idx = 0; 136 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 137 uint32_t *seenValues = malloc(3 * sizeof(uint32_t)); 138 [dict enumerateKeysAndUInt32sUsingBlock:^(NSString *aKey, uint32_t aValue, BOOL *stop) { 139 XCTAssertLessThan(idx, 3U); 140 seenKeys[idx] = aKey; 141 seenValues[idx] = aValue; 142 XCTAssertNotEqual(stop, NULL); 143 ++idx; 144 }]; 145 for (int i = 0; i < 3; ++i) { 146 BOOL foundKey = NO; 147 for (int j = 0; (j < 3) && !foundKey; ++j) { 148 if ([kKeys[i] isEqual:seenKeys[j]]) { 149 foundKey = YES; 150 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 151 } 152 } 153 XCTAssertTrue(foundKey, @"i = %d", i); 154 } 155 free(seenKeys); 156 free(seenValues); 157 158 // Stopping the enumeration. 159 idx = 0; 160 [dict enumerateKeysAndUInt32sUsingBlock:^(NSString *aKey, uint32_t aValue, BOOL *stop) { 161 #pragma unused(aKey, aValue) 162 if (idx == 1) *stop = YES; 163 XCTAssertNotEqual(idx, 2U); 164 ++idx; 165 }]; 166 [dict release]; 167} 168 169- (void)testEquality { 170 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 171 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 172 const uint32_t kValues1[] = { 100U, 101U, 102U }; 173 const uint32_t kValues2[] = { 100U, 103U, 102U }; 174 const uint32_t kValues3[] = { 100U, 101U, 102U, 103U }; 175 GPBStringUInt32Dictionary *dict1 = 176 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues1 177 forKeys:kKeys1 178 count:GPBARRAYSIZE(kValues1)]; 179 XCTAssertNotNil(dict1); 180 GPBStringUInt32Dictionary *dict1prime = 181 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues1 182 forKeys:kKeys1 183 count:GPBARRAYSIZE(kValues1)]; 184 XCTAssertNotNil(dict1prime); 185 GPBStringUInt32Dictionary *dict2 = 186 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues2 187 forKeys:kKeys1 188 count:GPBARRAYSIZE(kValues2)]; 189 XCTAssertNotNil(dict2); 190 GPBStringUInt32Dictionary *dict3 = 191 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues1 192 forKeys:kKeys2 193 count:GPBARRAYSIZE(kValues1)]; 194 XCTAssertNotNil(dict3); 195 GPBStringUInt32Dictionary *dict4 = 196 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues3 197 forKeys:kKeys1 198 count:GPBARRAYSIZE(kValues3)]; 199 XCTAssertNotNil(dict4); 200 201 // 1/1Prime should be different objects, but equal. 202 XCTAssertNotEqual(dict1, dict1prime); 203 XCTAssertEqualObjects(dict1, dict1prime); 204 // Equal, so they must have same hash. 205 XCTAssertEqual([dict1 hash], [dict1prime hash]); 206 207 // 2 is same keys, different values; not equal. 208 XCTAssertNotEqualObjects(dict1, dict2); 209 210 // 3 is different keys, same values; not equal. 211 XCTAssertNotEqualObjects(dict1, dict3); 212 213 // 4 extra pair; not equal 214 XCTAssertNotEqualObjects(dict1, dict4); 215 216 [dict1 release]; 217 [dict1prime release]; 218 [dict2 release]; 219 [dict3 release]; 220 [dict4 release]; 221} 222 223- (void)testCopy { 224 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 225 const uint32_t kValues[] = { 100U, 101U, 102U, 103U }; 226 GPBStringUInt32Dictionary *dict = 227 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues 228 forKeys:kKeys 229 count:GPBARRAYSIZE(kValues)]; 230 XCTAssertNotNil(dict); 231 232 GPBStringUInt32Dictionary *dict2 = [dict copy]; 233 XCTAssertNotNil(dict2); 234 235 // Should be new object but equal. 236 XCTAssertNotEqual(dict, dict2); 237 XCTAssertEqualObjects(dict, dict2); 238 XCTAssertTrue([dict2 isKindOfClass:[GPBStringUInt32Dictionary class]]); 239 240 [dict2 release]; 241 [dict release]; 242} 243 244- (void)testDictionaryFromDictionary { 245 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 246 const uint32_t kValues[] = { 100U, 101U, 102U, 103U }; 247 GPBStringUInt32Dictionary *dict = 248 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues 249 forKeys:kKeys 250 count:GPBARRAYSIZE(kValues)]; 251 XCTAssertNotNil(dict); 252 253 GPBStringUInt32Dictionary *dict2 = 254 [[GPBStringUInt32Dictionary alloc] initWithDictionary:dict]; 255 XCTAssertNotNil(dict2); 256 257 // Should be new pointer, but equal objects. 258 XCTAssertNotEqual(dict, dict2); 259 XCTAssertEqualObjects(dict, dict2); 260 [dict2 release]; 261 [dict release]; 262} 263 264- (void)testAdds { 265 GPBStringUInt32Dictionary *dict = [[GPBStringUInt32Dictionary alloc] init]; 266 XCTAssertNotNil(dict); 267 268 XCTAssertEqual(dict.count, 0U); 269 [dict setUInt32:100U forKey:@"foo"]; 270 XCTAssertEqual(dict.count, 1U); 271 272 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 273 const uint32_t kValues[] = { 101U, 102U, 103U }; 274 GPBStringUInt32Dictionary *dict2 = 275 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues 276 forKeys:kKeys 277 count:GPBARRAYSIZE(kValues)]; 278 XCTAssertNotNil(dict2); 279 [dict addEntriesFromDictionary:dict2]; 280 XCTAssertEqual(dict.count, 4U); 281 282 uint32_t value; 283 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 284 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 285 XCTAssertEqual(value, 100U); 286 XCTAssertTrue([dict getUInt32:NULL forKey:@"bar"]); 287 XCTAssertTrue([dict getUInt32:&value forKey:@"bar"]); 288 XCTAssertEqual(value, 101U); 289 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 290 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 291 XCTAssertEqual(value, 102U); 292 XCTAssertTrue([dict getUInt32:NULL forKey:@"mumble"]); 293 XCTAssertTrue([dict getUInt32:&value forKey:@"mumble"]); 294 XCTAssertEqual(value, 103U); 295 [dict2 release]; 296 [dict release]; 297} 298 299- (void)testRemove { 300 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 301 const uint32_t kValues[] = { 100U, 101U, 102U, 103U }; 302 GPBStringUInt32Dictionary *dict = 303 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues 304 forKeys:kKeys 305 count:GPBARRAYSIZE(kValues)]; 306 XCTAssertNotNil(dict); 307 XCTAssertEqual(dict.count, 4U); 308 309 [dict removeUInt32ForKey:@"bar"]; 310 XCTAssertEqual(dict.count, 3U); 311 uint32_t value; 312 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 313 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 314 XCTAssertEqual(value, 100U); 315 XCTAssertFalse([dict getUInt32:NULL forKey:@"bar"]); 316 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 317 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 318 XCTAssertEqual(value, 102U); 319 XCTAssertTrue([dict getUInt32:NULL forKey:@"mumble"]); 320 XCTAssertTrue([dict getUInt32:&value forKey:@"mumble"]); 321 XCTAssertEqual(value, 103U); 322 323 // Remove again does nothing. 324 [dict removeUInt32ForKey:@"bar"]; 325 XCTAssertEqual(dict.count, 3U); 326 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 327 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 328 XCTAssertEqual(value, 100U); 329 XCTAssertFalse([dict getUInt32:NULL forKey:@"bar"]); 330 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 331 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 332 XCTAssertEqual(value, 102U); 333 XCTAssertTrue([dict getUInt32:NULL forKey:@"mumble"]); 334 XCTAssertTrue([dict getUInt32:&value forKey:@"mumble"]); 335 XCTAssertEqual(value, 103U); 336 337 [dict removeUInt32ForKey:@"mumble"]; 338 XCTAssertEqual(dict.count, 2U); 339 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 340 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 341 XCTAssertEqual(value, 100U); 342 XCTAssertFalse([dict getUInt32:NULL forKey:@"bar"]); 343 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 344 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 345 XCTAssertEqual(value, 102U); 346 XCTAssertFalse([dict getUInt32:NULL forKey:@"mumble"]); 347 348 [dict removeAll]; 349 XCTAssertEqual(dict.count, 0U); 350 XCTAssertFalse([dict getUInt32:NULL forKey:@"foo"]); 351 XCTAssertFalse([dict getUInt32:NULL forKey:@"bar"]); 352 XCTAssertFalse([dict getUInt32:NULL forKey:@"baz"]); 353 XCTAssertFalse([dict getUInt32:NULL forKey:@"mumble"]); 354 [dict release]; 355} 356 357- (void)testInplaceMutation { 358 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 359 const uint32_t kValues[] = { 100U, 101U, 102U, 103U }; 360 GPBStringUInt32Dictionary *dict = 361 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues 362 forKeys:kKeys 363 count:GPBARRAYSIZE(kValues)]; 364 XCTAssertNotNil(dict); 365 XCTAssertEqual(dict.count, 4U); 366 uint32_t value; 367 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 368 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 369 XCTAssertEqual(value, 100U); 370 XCTAssertTrue([dict getUInt32:NULL forKey:@"bar"]); 371 XCTAssertTrue([dict getUInt32:&value forKey:@"bar"]); 372 XCTAssertEqual(value, 101U); 373 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 374 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 375 XCTAssertEqual(value, 102U); 376 XCTAssertTrue([dict getUInt32:NULL forKey:@"mumble"]); 377 XCTAssertTrue([dict getUInt32:&value forKey:@"mumble"]); 378 XCTAssertEqual(value, 103U); 379 380 [dict setUInt32:103U forKey:@"foo"]; 381 XCTAssertEqual(dict.count, 4U); 382 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 383 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 384 XCTAssertEqual(value, 103U); 385 XCTAssertTrue([dict getUInt32:NULL forKey:@"bar"]); 386 XCTAssertTrue([dict getUInt32:&value forKey:@"bar"]); 387 XCTAssertEqual(value, 101U); 388 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 389 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 390 XCTAssertEqual(value, 102U); 391 XCTAssertTrue([dict getUInt32:NULL forKey:@"mumble"]); 392 XCTAssertTrue([dict getUInt32:&value forKey:@"mumble"]); 393 XCTAssertEqual(value, 103U); 394 395 [dict setUInt32:101U forKey:@"mumble"]; 396 XCTAssertEqual(dict.count, 4U); 397 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 398 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 399 XCTAssertEqual(value, 103U); 400 XCTAssertTrue([dict getUInt32:NULL forKey:@"bar"]); 401 XCTAssertTrue([dict getUInt32:&value forKey:@"bar"]); 402 XCTAssertEqual(value, 101U); 403 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 404 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 405 XCTAssertEqual(value, 102U); 406 XCTAssertTrue([dict getUInt32:NULL forKey:@"mumble"]); 407 XCTAssertTrue([dict getUInt32:&value forKey:@"mumble"]); 408 XCTAssertEqual(value, 101U); 409 410 const NSString *kKeys2[] = { @"bar", @"baz" }; 411 const uint32_t kValues2[] = { 102U, 100U }; 412 GPBStringUInt32Dictionary *dict2 = 413 [[GPBStringUInt32Dictionary alloc] initWithUInt32s:kValues2 414 forKeys:kKeys2 415 count:GPBARRAYSIZE(kValues2)]; 416 XCTAssertNotNil(dict2); 417 [dict addEntriesFromDictionary:dict2]; 418 XCTAssertEqual(dict.count, 4U); 419 XCTAssertTrue([dict getUInt32:NULL forKey:@"foo"]); 420 XCTAssertTrue([dict getUInt32:&value forKey:@"foo"]); 421 XCTAssertEqual(value, 103U); 422 XCTAssertTrue([dict getUInt32:NULL forKey:@"bar"]); 423 XCTAssertTrue([dict getUInt32:&value forKey:@"bar"]); 424 XCTAssertEqual(value, 102U); 425 XCTAssertTrue([dict getUInt32:NULL forKey:@"baz"]); 426 XCTAssertTrue([dict getUInt32:&value forKey:@"baz"]); 427 XCTAssertEqual(value, 100U); 428 XCTAssertTrue([dict getUInt32:NULL forKey:@"mumble"]); 429 XCTAssertTrue([dict getUInt32:&value forKey:@"mumble"]); 430 XCTAssertEqual(value, 101U); 431 432 [dict2 release]; 433 [dict release]; 434} 435 436@end 437 438#pragma mark - String -> Int32 439 440@interface GPBStringInt32DictionaryTests : XCTestCase 441@end 442 443@implementation GPBStringInt32DictionaryTests 444 445- (void)testEmpty { 446 GPBStringInt32Dictionary *dict = [[GPBStringInt32Dictionary alloc] init]; 447 XCTAssertNotNil(dict); 448 XCTAssertEqual(dict.count, 0U); 449 XCTAssertFalse([dict getInt32:NULL forKey:@"foo"]); 450 [dict enumerateKeysAndInt32sUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 451 #pragma unused(aKey, aValue, stop) 452 XCTFail(@"Shouldn't get here!"); 453 }]; 454 [dict release]; 455} 456 457- (void)testOne { 458 GPBStringInt32Dictionary *dict = [[GPBStringInt32Dictionary alloc] init]; 459 [dict setInt32:200 forKey:@"foo"]; 460 XCTAssertNotNil(dict); 461 XCTAssertEqual(dict.count, 1U); 462 int32_t value; 463 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 464 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 465 XCTAssertEqual(value, 200); 466 XCTAssertFalse([dict getInt32:NULL forKey:@"bar"]); 467 [dict enumerateKeysAndInt32sUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 468 XCTAssertEqualObjects(aKey, @"foo"); 469 XCTAssertEqual(aValue, 200); 470 XCTAssertNotEqual(stop, NULL); 471 }]; 472 [dict release]; 473} 474 475- (void)testBasics { 476 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 477 const int32_t kValues[] = { 200, 201, 202 }; 478 GPBStringInt32Dictionary *dict = 479 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues 480 forKeys:kKeys 481 count:GPBARRAYSIZE(kValues)]; 482 XCTAssertNotNil(dict); 483 XCTAssertEqual(dict.count, 3U); 484 int32_t value; 485 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 486 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 487 XCTAssertEqual(value, 200); 488 XCTAssertTrue([dict getInt32:NULL forKey:@"bar"]); 489 XCTAssertTrue([dict getInt32:&value forKey:@"bar"]); 490 XCTAssertEqual(value, 201); 491 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 492 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 493 XCTAssertEqual(value, 202); 494 XCTAssertFalse([dict getInt32:NULL forKey:@"mumble"]); 495 496 __block NSUInteger idx = 0; 497 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 498 int32_t *seenValues = malloc(3 * sizeof(int32_t)); 499 [dict enumerateKeysAndInt32sUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 500 XCTAssertLessThan(idx, 3U); 501 seenKeys[idx] = aKey; 502 seenValues[idx] = aValue; 503 XCTAssertNotEqual(stop, NULL); 504 ++idx; 505 }]; 506 for (int i = 0; i < 3; ++i) { 507 BOOL foundKey = NO; 508 for (int j = 0; (j < 3) && !foundKey; ++j) { 509 if ([kKeys[i] isEqual:seenKeys[j]]) { 510 foundKey = YES; 511 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 512 } 513 } 514 XCTAssertTrue(foundKey, @"i = %d", i); 515 } 516 free(seenKeys); 517 free(seenValues); 518 519 // Stopping the enumeration. 520 idx = 0; 521 [dict enumerateKeysAndInt32sUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 522 #pragma unused(aKey, aValue) 523 if (idx == 1) *stop = YES; 524 XCTAssertNotEqual(idx, 2U); 525 ++idx; 526 }]; 527 [dict release]; 528} 529 530- (void)testEquality { 531 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 532 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 533 const int32_t kValues1[] = { 200, 201, 202 }; 534 const int32_t kValues2[] = { 200, 203, 202 }; 535 const int32_t kValues3[] = { 200, 201, 202, 203 }; 536 GPBStringInt32Dictionary *dict1 = 537 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues1 538 forKeys:kKeys1 539 count:GPBARRAYSIZE(kValues1)]; 540 XCTAssertNotNil(dict1); 541 GPBStringInt32Dictionary *dict1prime = 542 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues1 543 forKeys:kKeys1 544 count:GPBARRAYSIZE(kValues1)]; 545 XCTAssertNotNil(dict1prime); 546 GPBStringInt32Dictionary *dict2 = 547 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues2 548 forKeys:kKeys1 549 count:GPBARRAYSIZE(kValues2)]; 550 XCTAssertNotNil(dict2); 551 GPBStringInt32Dictionary *dict3 = 552 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues1 553 forKeys:kKeys2 554 count:GPBARRAYSIZE(kValues1)]; 555 XCTAssertNotNil(dict3); 556 GPBStringInt32Dictionary *dict4 = 557 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues3 558 forKeys:kKeys1 559 count:GPBARRAYSIZE(kValues3)]; 560 XCTAssertNotNil(dict4); 561 562 // 1/1Prime should be different objects, but equal. 563 XCTAssertNotEqual(dict1, dict1prime); 564 XCTAssertEqualObjects(dict1, dict1prime); 565 // Equal, so they must have same hash. 566 XCTAssertEqual([dict1 hash], [dict1prime hash]); 567 568 // 2 is same keys, different values; not equal. 569 XCTAssertNotEqualObjects(dict1, dict2); 570 571 // 3 is different keys, same values; not equal. 572 XCTAssertNotEqualObjects(dict1, dict3); 573 574 // 4 extra pair; not equal 575 XCTAssertNotEqualObjects(dict1, dict4); 576 577 [dict1 release]; 578 [dict1prime release]; 579 [dict2 release]; 580 [dict3 release]; 581 [dict4 release]; 582} 583 584- (void)testCopy { 585 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 586 const int32_t kValues[] = { 200, 201, 202, 203 }; 587 GPBStringInt32Dictionary *dict = 588 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues 589 forKeys:kKeys 590 count:GPBARRAYSIZE(kValues)]; 591 XCTAssertNotNil(dict); 592 593 GPBStringInt32Dictionary *dict2 = [dict copy]; 594 XCTAssertNotNil(dict2); 595 596 // Should be new object but equal. 597 XCTAssertNotEqual(dict, dict2); 598 XCTAssertEqualObjects(dict, dict2); 599 XCTAssertTrue([dict2 isKindOfClass:[GPBStringInt32Dictionary class]]); 600 601 [dict2 release]; 602 [dict release]; 603} 604 605- (void)testDictionaryFromDictionary { 606 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 607 const int32_t kValues[] = { 200, 201, 202, 203 }; 608 GPBStringInt32Dictionary *dict = 609 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues 610 forKeys:kKeys 611 count:GPBARRAYSIZE(kValues)]; 612 XCTAssertNotNil(dict); 613 614 GPBStringInt32Dictionary *dict2 = 615 [[GPBStringInt32Dictionary alloc] initWithDictionary:dict]; 616 XCTAssertNotNil(dict2); 617 618 // Should be new pointer, but equal objects. 619 XCTAssertNotEqual(dict, dict2); 620 XCTAssertEqualObjects(dict, dict2); 621 [dict2 release]; 622 [dict release]; 623} 624 625- (void)testAdds { 626 GPBStringInt32Dictionary *dict = [[GPBStringInt32Dictionary alloc] init]; 627 XCTAssertNotNil(dict); 628 629 XCTAssertEqual(dict.count, 0U); 630 [dict setInt32:200 forKey:@"foo"]; 631 XCTAssertEqual(dict.count, 1U); 632 633 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 634 const int32_t kValues[] = { 201, 202, 203 }; 635 GPBStringInt32Dictionary *dict2 = 636 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues 637 forKeys:kKeys 638 count:GPBARRAYSIZE(kValues)]; 639 XCTAssertNotNil(dict2); 640 [dict addEntriesFromDictionary:dict2]; 641 XCTAssertEqual(dict.count, 4U); 642 643 int32_t value; 644 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 645 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 646 XCTAssertEqual(value, 200); 647 XCTAssertTrue([dict getInt32:NULL forKey:@"bar"]); 648 XCTAssertTrue([dict getInt32:&value forKey:@"bar"]); 649 XCTAssertEqual(value, 201); 650 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 651 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 652 XCTAssertEqual(value, 202); 653 XCTAssertTrue([dict getInt32:NULL forKey:@"mumble"]); 654 XCTAssertTrue([dict getInt32:&value forKey:@"mumble"]); 655 XCTAssertEqual(value, 203); 656 [dict2 release]; 657 [dict release]; 658} 659 660- (void)testRemove { 661 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 662 const int32_t kValues[] = { 200, 201, 202, 203 }; 663 GPBStringInt32Dictionary *dict = 664 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues 665 forKeys:kKeys 666 count:GPBARRAYSIZE(kValues)]; 667 XCTAssertNotNil(dict); 668 XCTAssertEqual(dict.count, 4U); 669 670 [dict removeInt32ForKey:@"bar"]; 671 XCTAssertEqual(dict.count, 3U); 672 int32_t value; 673 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 674 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 675 XCTAssertEqual(value, 200); 676 XCTAssertFalse([dict getInt32:NULL forKey:@"bar"]); 677 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 678 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 679 XCTAssertEqual(value, 202); 680 XCTAssertTrue([dict getInt32:NULL forKey:@"mumble"]); 681 XCTAssertTrue([dict getInt32:&value forKey:@"mumble"]); 682 XCTAssertEqual(value, 203); 683 684 // Remove again does nothing. 685 [dict removeInt32ForKey:@"bar"]; 686 XCTAssertEqual(dict.count, 3U); 687 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 688 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 689 XCTAssertEqual(value, 200); 690 XCTAssertFalse([dict getInt32:NULL forKey:@"bar"]); 691 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 692 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 693 XCTAssertEqual(value, 202); 694 XCTAssertTrue([dict getInt32:NULL forKey:@"mumble"]); 695 XCTAssertTrue([dict getInt32:&value forKey:@"mumble"]); 696 XCTAssertEqual(value, 203); 697 698 [dict removeInt32ForKey:@"mumble"]; 699 XCTAssertEqual(dict.count, 2U); 700 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 701 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 702 XCTAssertEqual(value, 200); 703 XCTAssertFalse([dict getInt32:NULL forKey:@"bar"]); 704 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 705 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 706 XCTAssertEqual(value, 202); 707 XCTAssertFalse([dict getInt32:NULL forKey:@"mumble"]); 708 709 [dict removeAll]; 710 XCTAssertEqual(dict.count, 0U); 711 XCTAssertFalse([dict getInt32:NULL forKey:@"foo"]); 712 XCTAssertFalse([dict getInt32:NULL forKey:@"bar"]); 713 XCTAssertFalse([dict getInt32:NULL forKey:@"baz"]); 714 XCTAssertFalse([dict getInt32:NULL forKey:@"mumble"]); 715 [dict release]; 716} 717 718- (void)testInplaceMutation { 719 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 720 const int32_t kValues[] = { 200, 201, 202, 203 }; 721 GPBStringInt32Dictionary *dict = 722 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues 723 forKeys:kKeys 724 count:GPBARRAYSIZE(kValues)]; 725 XCTAssertNotNil(dict); 726 XCTAssertEqual(dict.count, 4U); 727 int32_t value; 728 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 729 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 730 XCTAssertEqual(value, 200); 731 XCTAssertTrue([dict getInt32:NULL forKey:@"bar"]); 732 XCTAssertTrue([dict getInt32:&value forKey:@"bar"]); 733 XCTAssertEqual(value, 201); 734 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 735 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 736 XCTAssertEqual(value, 202); 737 XCTAssertTrue([dict getInt32:NULL forKey:@"mumble"]); 738 XCTAssertTrue([dict getInt32:&value forKey:@"mumble"]); 739 XCTAssertEqual(value, 203); 740 741 [dict setInt32:203 forKey:@"foo"]; 742 XCTAssertEqual(dict.count, 4U); 743 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 744 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 745 XCTAssertEqual(value, 203); 746 XCTAssertTrue([dict getInt32:NULL forKey:@"bar"]); 747 XCTAssertTrue([dict getInt32:&value forKey:@"bar"]); 748 XCTAssertEqual(value, 201); 749 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 750 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 751 XCTAssertEqual(value, 202); 752 XCTAssertTrue([dict getInt32:NULL forKey:@"mumble"]); 753 XCTAssertTrue([dict getInt32:&value forKey:@"mumble"]); 754 XCTAssertEqual(value, 203); 755 756 [dict setInt32:201 forKey:@"mumble"]; 757 XCTAssertEqual(dict.count, 4U); 758 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 759 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 760 XCTAssertEqual(value, 203); 761 XCTAssertTrue([dict getInt32:NULL forKey:@"bar"]); 762 XCTAssertTrue([dict getInt32:&value forKey:@"bar"]); 763 XCTAssertEqual(value, 201); 764 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 765 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 766 XCTAssertEqual(value, 202); 767 XCTAssertTrue([dict getInt32:NULL forKey:@"mumble"]); 768 XCTAssertTrue([dict getInt32:&value forKey:@"mumble"]); 769 XCTAssertEqual(value, 201); 770 771 const NSString *kKeys2[] = { @"bar", @"baz" }; 772 const int32_t kValues2[] = { 202, 200 }; 773 GPBStringInt32Dictionary *dict2 = 774 [[GPBStringInt32Dictionary alloc] initWithInt32s:kValues2 775 forKeys:kKeys2 776 count:GPBARRAYSIZE(kValues2)]; 777 XCTAssertNotNil(dict2); 778 [dict addEntriesFromDictionary:dict2]; 779 XCTAssertEqual(dict.count, 4U); 780 XCTAssertTrue([dict getInt32:NULL forKey:@"foo"]); 781 XCTAssertTrue([dict getInt32:&value forKey:@"foo"]); 782 XCTAssertEqual(value, 203); 783 XCTAssertTrue([dict getInt32:NULL forKey:@"bar"]); 784 XCTAssertTrue([dict getInt32:&value forKey:@"bar"]); 785 XCTAssertEqual(value, 202); 786 XCTAssertTrue([dict getInt32:NULL forKey:@"baz"]); 787 XCTAssertTrue([dict getInt32:&value forKey:@"baz"]); 788 XCTAssertEqual(value, 200); 789 XCTAssertTrue([dict getInt32:NULL forKey:@"mumble"]); 790 XCTAssertTrue([dict getInt32:&value forKey:@"mumble"]); 791 XCTAssertEqual(value, 201); 792 793 [dict2 release]; 794 [dict release]; 795} 796 797@end 798 799#pragma mark - String -> UInt64 800 801@interface GPBStringUInt64DictionaryTests : XCTestCase 802@end 803 804@implementation GPBStringUInt64DictionaryTests 805 806- (void)testEmpty { 807 GPBStringUInt64Dictionary *dict = [[GPBStringUInt64Dictionary alloc] init]; 808 XCTAssertNotNil(dict); 809 XCTAssertEqual(dict.count, 0U); 810 XCTAssertFalse([dict getUInt64:NULL forKey:@"foo"]); 811 [dict enumerateKeysAndUInt64sUsingBlock:^(NSString *aKey, uint64_t aValue, BOOL *stop) { 812 #pragma unused(aKey, aValue, stop) 813 XCTFail(@"Shouldn't get here!"); 814 }]; 815 [dict release]; 816} 817 818- (void)testOne { 819 GPBStringUInt64Dictionary *dict = [[GPBStringUInt64Dictionary alloc] init]; 820 [dict setUInt64:300U forKey:@"foo"]; 821 XCTAssertNotNil(dict); 822 XCTAssertEqual(dict.count, 1U); 823 uint64_t value; 824 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 825 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 826 XCTAssertEqual(value, 300U); 827 XCTAssertFalse([dict getUInt64:NULL forKey:@"bar"]); 828 [dict enumerateKeysAndUInt64sUsingBlock:^(NSString *aKey, uint64_t aValue, BOOL *stop) { 829 XCTAssertEqualObjects(aKey, @"foo"); 830 XCTAssertEqual(aValue, 300U); 831 XCTAssertNotEqual(stop, NULL); 832 }]; 833 [dict release]; 834} 835 836- (void)testBasics { 837 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 838 const uint64_t kValues[] = { 300U, 301U, 302U }; 839 GPBStringUInt64Dictionary *dict = 840 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues 841 forKeys:kKeys 842 count:GPBARRAYSIZE(kValues)]; 843 XCTAssertNotNil(dict); 844 XCTAssertEqual(dict.count, 3U); 845 uint64_t value; 846 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 847 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 848 XCTAssertEqual(value, 300U); 849 XCTAssertTrue([dict getUInt64:NULL forKey:@"bar"]); 850 XCTAssertTrue([dict getUInt64:&value forKey:@"bar"]); 851 XCTAssertEqual(value, 301U); 852 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 853 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 854 XCTAssertEqual(value, 302U); 855 XCTAssertFalse([dict getUInt64:NULL forKey:@"mumble"]); 856 857 __block NSUInteger idx = 0; 858 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 859 uint64_t *seenValues = malloc(3 * sizeof(uint64_t)); 860 [dict enumerateKeysAndUInt64sUsingBlock:^(NSString *aKey, uint64_t aValue, BOOL *stop) { 861 XCTAssertLessThan(idx, 3U); 862 seenKeys[idx] = aKey; 863 seenValues[idx] = aValue; 864 XCTAssertNotEqual(stop, NULL); 865 ++idx; 866 }]; 867 for (int i = 0; i < 3; ++i) { 868 BOOL foundKey = NO; 869 for (int j = 0; (j < 3) && !foundKey; ++j) { 870 if ([kKeys[i] isEqual:seenKeys[j]]) { 871 foundKey = YES; 872 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 873 } 874 } 875 XCTAssertTrue(foundKey, @"i = %d", i); 876 } 877 free(seenKeys); 878 free(seenValues); 879 880 // Stopping the enumeration. 881 idx = 0; 882 [dict enumerateKeysAndUInt64sUsingBlock:^(NSString *aKey, uint64_t aValue, BOOL *stop) { 883 #pragma unused(aKey, aValue) 884 if (idx == 1) *stop = YES; 885 XCTAssertNotEqual(idx, 2U); 886 ++idx; 887 }]; 888 [dict release]; 889} 890 891- (void)testEquality { 892 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 893 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 894 const uint64_t kValues1[] = { 300U, 301U, 302U }; 895 const uint64_t kValues2[] = { 300U, 303U, 302U }; 896 const uint64_t kValues3[] = { 300U, 301U, 302U, 303U }; 897 GPBStringUInt64Dictionary *dict1 = 898 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues1 899 forKeys:kKeys1 900 count:GPBARRAYSIZE(kValues1)]; 901 XCTAssertNotNil(dict1); 902 GPBStringUInt64Dictionary *dict1prime = 903 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues1 904 forKeys:kKeys1 905 count:GPBARRAYSIZE(kValues1)]; 906 XCTAssertNotNil(dict1prime); 907 GPBStringUInt64Dictionary *dict2 = 908 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues2 909 forKeys:kKeys1 910 count:GPBARRAYSIZE(kValues2)]; 911 XCTAssertNotNil(dict2); 912 GPBStringUInt64Dictionary *dict3 = 913 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues1 914 forKeys:kKeys2 915 count:GPBARRAYSIZE(kValues1)]; 916 XCTAssertNotNil(dict3); 917 GPBStringUInt64Dictionary *dict4 = 918 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues3 919 forKeys:kKeys1 920 count:GPBARRAYSIZE(kValues3)]; 921 XCTAssertNotNil(dict4); 922 923 // 1/1Prime should be different objects, but equal. 924 XCTAssertNotEqual(dict1, dict1prime); 925 XCTAssertEqualObjects(dict1, dict1prime); 926 // Equal, so they must have same hash. 927 XCTAssertEqual([dict1 hash], [dict1prime hash]); 928 929 // 2 is same keys, different values; not equal. 930 XCTAssertNotEqualObjects(dict1, dict2); 931 932 // 3 is different keys, same values; not equal. 933 XCTAssertNotEqualObjects(dict1, dict3); 934 935 // 4 extra pair; not equal 936 XCTAssertNotEqualObjects(dict1, dict4); 937 938 [dict1 release]; 939 [dict1prime release]; 940 [dict2 release]; 941 [dict3 release]; 942 [dict4 release]; 943} 944 945- (void)testCopy { 946 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 947 const uint64_t kValues[] = { 300U, 301U, 302U, 303U }; 948 GPBStringUInt64Dictionary *dict = 949 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues 950 forKeys:kKeys 951 count:GPBARRAYSIZE(kValues)]; 952 XCTAssertNotNil(dict); 953 954 GPBStringUInt64Dictionary *dict2 = [dict copy]; 955 XCTAssertNotNil(dict2); 956 957 // Should be new object but equal. 958 XCTAssertNotEqual(dict, dict2); 959 XCTAssertEqualObjects(dict, dict2); 960 XCTAssertTrue([dict2 isKindOfClass:[GPBStringUInt64Dictionary class]]); 961 962 [dict2 release]; 963 [dict release]; 964} 965 966- (void)testDictionaryFromDictionary { 967 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 968 const uint64_t kValues[] = { 300U, 301U, 302U, 303U }; 969 GPBStringUInt64Dictionary *dict = 970 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues 971 forKeys:kKeys 972 count:GPBARRAYSIZE(kValues)]; 973 XCTAssertNotNil(dict); 974 975 GPBStringUInt64Dictionary *dict2 = 976 [[GPBStringUInt64Dictionary alloc] initWithDictionary:dict]; 977 XCTAssertNotNil(dict2); 978 979 // Should be new pointer, but equal objects. 980 XCTAssertNotEqual(dict, dict2); 981 XCTAssertEqualObjects(dict, dict2); 982 [dict2 release]; 983 [dict release]; 984} 985 986- (void)testAdds { 987 GPBStringUInt64Dictionary *dict = [[GPBStringUInt64Dictionary alloc] init]; 988 XCTAssertNotNil(dict); 989 990 XCTAssertEqual(dict.count, 0U); 991 [dict setUInt64:300U forKey:@"foo"]; 992 XCTAssertEqual(dict.count, 1U); 993 994 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 995 const uint64_t kValues[] = { 301U, 302U, 303U }; 996 GPBStringUInt64Dictionary *dict2 = 997 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues 998 forKeys:kKeys 999 count:GPBARRAYSIZE(kValues)]; 1000 XCTAssertNotNil(dict2); 1001 [dict addEntriesFromDictionary:dict2]; 1002 XCTAssertEqual(dict.count, 4U); 1003 1004 uint64_t value; 1005 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1006 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1007 XCTAssertEqual(value, 300U); 1008 XCTAssertTrue([dict getUInt64:NULL forKey:@"bar"]); 1009 XCTAssertTrue([dict getUInt64:&value forKey:@"bar"]); 1010 XCTAssertEqual(value, 301U); 1011 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1012 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1013 XCTAssertEqual(value, 302U); 1014 XCTAssertTrue([dict getUInt64:NULL forKey:@"mumble"]); 1015 XCTAssertTrue([dict getUInt64:&value forKey:@"mumble"]); 1016 XCTAssertEqual(value, 303U); 1017 [dict2 release]; 1018 [dict release]; 1019} 1020 1021- (void)testRemove { 1022 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1023 const uint64_t kValues[] = { 300U, 301U, 302U, 303U }; 1024 GPBStringUInt64Dictionary *dict = 1025 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues 1026 forKeys:kKeys 1027 count:GPBARRAYSIZE(kValues)]; 1028 XCTAssertNotNil(dict); 1029 XCTAssertEqual(dict.count, 4U); 1030 1031 [dict removeUInt64ForKey:@"bar"]; 1032 XCTAssertEqual(dict.count, 3U); 1033 uint64_t value; 1034 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1035 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1036 XCTAssertEqual(value, 300U); 1037 XCTAssertFalse([dict getUInt64:NULL forKey:@"bar"]); 1038 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1039 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1040 XCTAssertEqual(value, 302U); 1041 XCTAssertTrue([dict getUInt64:NULL forKey:@"mumble"]); 1042 XCTAssertTrue([dict getUInt64:&value forKey:@"mumble"]); 1043 XCTAssertEqual(value, 303U); 1044 1045 // Remove again does nothing. 1046 [dict removeUInt64ForKey:@"bar"]; 1047 XCTAssertEqual(dict.count, 3U); 1048 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1049 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1050 XCTAssertEqual(value, 300U); 1051 XCTAssertFalse([dict getUInt64:NULL forKey:@"bar"]); 1052 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1053 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1054 XCTAssertEqual(value, 302U); 1055 XCTAssertTrue([dict getUInt64:NULL forKey:@"mumble"]); 1056 XCTAssertTrue([dict getUInt64:&value forKey:@"mumble"]); 1057 XCTAssertEqual(value, 303U); 1058 1059 [dict removeUInt64ForKey:@"mumble"]; 1060 XCTAssertEqual(dict.count, 2U); 1061 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1062 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1063 XCTAssertEqual(value, 300U); 1064 XCTAssertFalse([dict getUInt64:NULL forKey:@"bar"]); 1065 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1066 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1067 XCTAssertEqual(value, 302U); 1068 XCTAssertFalse([dict getUInt64:NULL forKey:@"mumble"]); 1069 1070 [dict removeAll]; 1071 XCTAssertEqual(dict.count, 0U); 1072 XCTAssertFalse([dict getUInt64:NULL forKey:@"foo"]); 1073 XCTAssertFalse([dict getUInt64:NULL forKey:@"bar"]); 1074 XCTAssertFalse([dict getUInt64:NULL forKey:@"baz"]); 1075 XCTAssertFalse([dict getUInt64:NULL forKey:@"mumble"]); 1076 [dict release]; 1077} 1078 1079- (void)testInplaceMutation { 1080 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1081 const uint64_t kValues[] = { 300U, 301U, 302U, 303U }; 1082 GPBStringUInt64Dictionary *dict = 1083 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues 1084 forKeys:kKeys 1085 count:GPBARRAYSIZE(kValues)]; 1086 XCTAssertNotNil(dict); 1087 XCTAssertEqual(dict.count, 4U); 1088 uint64_t value; 1089 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1090 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1091 XCTAssertEqual(value, 300U); 1092 XCTAssertTrue([dict getUInt64:NULL forKey:@"bar"]); 1093 XCTAssertTrue([dict getUInt64:&value forKey:@"bar"]); 1094 XCTAssertEqual(value, 301U); 1095 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1096 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1097 XCTAssertEqual(value, 302U); 1098 XCTAssertTrue([dict getUInt64:NULL forKey:@"mumble"]); 1099 XCTAssertTrue([dict getUInt64:&value forKey:@"mumble"]); 1100 XCTAssertEqual(value, 303U); 1101 1102 [dict setUInt64:303U forKey:@"foo"]; 1103 XCTAssertEqual(dict.count, 4U); 1104 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1105 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1106 XCTAssertEqual(value, 303U); 1107 XCTAssertTrue([dict getUInt64:NULL forKey:@"bar"]); 1108 XCTAssertTrue([dict getUInt64:&value forKey:@"bar"]); 1109 XCTAssertEqual(value, 301U); 1110 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1111 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1112 XCTAssertEqual(value, 302U); 1113 XCTAssertTrue([dict getUInt64:NULL forKey:@"mumble"]); 1114 XCTAssertTrue([dict getUInt64:&value forKey:@"mumble"]); 1115 XCTAssertEqual(value, 303U); 1116 1117 [dict setUInt64:301U forKey:@"mumble"]; 1118 XCTAssertEqual(dict.count, 4U); 1119 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1120 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1121 XCTAssertEqual(value, 303U); 1122 XCTAssertTrue([dict getUInt64:NULL forKey:@"bar"]); 1123 XCTAssertTrue([dict getUInt64:&value forKey:@"bar"]); 1124 XCTAssertEqual(value, 301U); 1125 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1126 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1127 XCTAssertEqual(value, 302U); 1128 XCTAssertTrue([dict getUInt64:NULL forKey:@"mumble"]); 1129 XCTAssertTrue([dict getUInt64:&value forKey:@"mumble"]); 1130 XCTAssertEqual(value, 301U); 1131 1132 const NSString *kKeys2[] = { @"bar", @"baz" }; 1133 const uint64_t kValues2[] = { 302U, 300U }; 1134 GPBStringUInt64Dictionary *dict2 = 1135 [[GPBStringUInt64Dictionary alloc] initWithUInt64s:kValues2 1136 forKeys:kKeys2 1137 count:GPBARRAYSIZE(kValues2)]; 1138 XCTAssertNotNil(dict2); 1139 [dict addEntriesFromDictionary:dict2]; 1140 XCTAssertEqual(dict.count, 4U); 1141 XCTAssertTrue([dict getUInt64:NULL forKey:@"foo"]); 1142 XCTAssertTrue([dict getUInt64:&value forKey:@"foo"]); 1143 XCTAssertEqual(value, 303U); 1144 XCTAssertTrue([dict getUInt64:NULL forKey:@"bar"]); 1145 XCTAssertTrue([dict getUInt64:&value forKey:@"bar"]); 1146 XCTAssertEqual(value, 302U); 1147 XCTAssertTrue([dict getUInt64:NULL forKey:@"baz"]); 1148 XCTAssertTrue([dict getUInt64:&value forKey:@"baz"]); 1149 XCTAssertEqual(value, 300U); 1150 XCTAssertTrue([dict getUInt64:NULL forKey:@"mumble"]); 1151 XCTAssertTrue([dict getUInt64:&value forKey:@"mumble"]); 1152 XCTAssertEqual(value, 301U); 1153 1154 [dict2 release]; 1155 [dict release]; 1156} 1157 1158@end 1159 1160#pragma mark - String -> Int64 1161 1162@interface GPBStringInt64DictionaryTests : XCTestCase 1163@end 1164 1165@implementation GPBStringInt64DictionaryTests 1166 1167- (void)testEmpty { 1168 GPBStringInt64Dictionary *dict = [[GPBStringInt64Dictionary alloc] init]; 1169 XCTAssertNotNil(dict); 1170 XCTAssertEqual(dict.count, 0U); 1171 XCTAssertFalse([dict getInt64:NULL forKey:@"foo"]); 1172 [dict enumerateKeysAndInt64sUsingBlock:^(NSString *aKey, int64_t aValue, BOOL *stop) { 1173 #pragma unused(aKey, aValue, stop) 1174 XCTFail(@"Shouldn't get here!"); 1175 }]; 1176 [dict release]; 1177} 1178 1179- (void)testOne { 1180 GPBStringInt64Dictionary *dict = [[GPBStringInt64Dictionary alloc] init]; 1181 [dict setInt64:400 forKey:@"foo"]; 1182 XCTAssertNotNil(dict); 1183 XCTAssertEqual(dict.count, 1U); 1184 int64_t value; 1185 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1186 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1187 XCTAssertEqual(value, 400); 1188 XCTAssertFalse([dict getInt64:NULL forKey:@"bar"]); 1189 [dict enumerateKeysAndInt64sUsingBlock:^(NSString *aKey, int64_t aValue, BOOL *stop) { 1190 XCTAssertEqualObjects(aKey, @"foo"); 1191 XCTAssertEqual(aValue, 400); 1192 XCTAssertNotEqual(stop, NULL); 1193 }]; 1194 [dict release]; 1195} 1196 1197- (void)testBasics { 1198 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 1199 const int64_t kValues[] = { 400, 401, 402 }; 1200 GPBStringInt64Dictionary *dict = 1201 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues 1202 forKeys:kKeys 1203 count:GPBARRAYSIZE(kValues)]; 1204 XCTAssertNotNil(dict); 1205 XCTAssertEqual(dict.count, 3U); 1206 int64_t value; 1207 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1208 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1209 XCTAssertEqual(value, 400); 1210 XCTAssertTrue([dict getInt64:NULL forKey:@"bar"]); 1211 XCTAssertTrue([dict getInt64:&value forKey:@"bar"]); 1212 XCTAssertEqual(value, 401); 1213 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1214 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1215 XCTAssertEqual(value, 402); 1216 XCTAssertFalse([dict getInt64:NULL forKey:@"mumble"]); 1217 1218 __block NSUInteger idx = 0; 1219 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 1220 int64_t *seenValues = malloc(3 * sizeof(int64_t)); 1221 [dict enumerateKeysAndInt64sUsingBlock:^(NSString *aKey, int64_t aValue, BOOL *stop) { 1222 XCTAssertLessThan(idx, 3U); 1223 seenKeys[idx] = aKey; 1224 seenValues[idx] = aValue; 1225 XCTAssertNotEqual(stop, NULL); 1226 ++idx; 1227 }]; 1228 for (int i = 0; i < 3; ++i) { 1229 BOOL foundKey = NO; 1230 for (int j = 0; (j < 3) && !foundKey; ++j) { 1231 if ([kKeys[i] isEqual:seenKeys[j]]) { 1232 foundKey = YES; 1233 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 1234 } 1235 } 1236 XCTAssertTrue(foundKey, @"i = %d", i); 1237 } 1238 free(seenKeys); 1239 free(seenValues); 1240 1241 // Stopping the enumeration. 1242 idx = 0; 1243 [dict enumerateKeysAndInt64sUsingBlock:^(NSString *aKey, int64_t aValue, BOOL *stop) { 1244 #pragma unused(aKey, aValue) 1245 if (idx == 1) *stop = YES; 1246 XCTAssertNotEqual(idx, 2U); 1247 ++idx; 1248 }]; 1249 [dict release]; 1250} 1251 1252- (void)testEquality { 1253 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 1254 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 1255 const int64_t kValues1[] = { 400, 401, 402 }; 1256 const int64_t kValues2[] = { 400, 403, 402 }; 1257 const int64_t kValues3[] = { 400, 401, 402, 403 }; 1258 GPBStringInt64Dictionary *dict1 = 1259 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues1 1260 forKeys:kKeys1 1261 count:GPBARRAYSIZE(kValues1)]; 1262 XCTAssertNotNil(dict1); 1263 GPBStringInt64Dictionary *dict1prime = 1264 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues1 1265 forKeys:kKeys1 1266 count:GPBARRAYSIZE(kValues1)]; 1267 XCTAssertNotNil(dict1prime); 1268 GPBStringInt64Dictionary *dict2 = 1269 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues2 1270 forKeys:kKeys1 1271 count:GPBARRAYSIZE(kValues2)]; 1272 XCTAssertNotNil(dict2); 1273 GPBStringInt64Dictionary *dict3 = 1274 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues1 1275 forKeys:kKeys2 1276 count:GPBARRAYSIZE(kValues1)]; 1277 XCTAssertNotNil(dict3); 1278 GPBStringInt64Dictionary *dict4 = 1279 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues3 1280 forKeys:kKeys1 1281 count:GPBARRAYSIZE(kValues3)]; 1282 XCTAssertNotNil(dict4); 1283 1284 // 1/1Prime should be different objects, but equal. 1285 XCTAssertNotEqual(dict1, dict1prime); 1286 XCTAssertEqualObjects(dict1, dict1prime); 1287 // Equal, so they must have same hash. 1288 XCTAssertEqual([dict1 hash], [dict1prime hash]); 1289 1290 // 2 is same keys, different values; not equal. 1291 XCTAssertNotEqualObjects(dict1, dict2); 1292 1293 // 3 is different keys, same values; not equal. 1294 XCTAssertNotEqualObjects(dict1, dict3); 1295 1296 // 4 extra pair; not equal 1297 XCTAssertNotEqualObjects(dict1, dict4); 1298 1299 [dict1 release]; 1300 [dict1prime release]; 1301 [dict2 release]; 1302 [dict3 release]; 1303 [dict4 release]; 1304} 1305 1306- (void)testCopy { 1307 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1308 const int64_t kValues[] = { 400, 401, 402, 403 }; 1309 GPBStringInt64Dictionary *dict = 1310 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues 1311 forKeys:kKeys 1312 count:GPBARRAYSIZE(kValues)]; 1313 XCTAssertNotNil(dict); 1314 1315 GPBStringInt64Dictionary *dict2 = [dict copy]; 1316 XCTAssertNotNil(dict2); 1317 1318 // Should be new object but equal. 1319 XCTAssertNotEqual(dict, dict2); 1320 XCTAssertEqualObjects(dict, dict2); 1321 XCTAssertTrue([dict2 isKindOfClass:[GPBStringInt64Dictionary class]]); 1322 1323 [dict2 release]; 1324 [dict release]; 1325} 1326 1327- (void)testDictionaryFromDictionary { 1328 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1329 const int64_t kValues[] = { 400, 401, 402, 403 }; 1330 GPBStringInt64Dictionary *dict = 1331 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues 1332 forKeys:kKeys 1333 count:GPBARRAYSIZE(kValues)]; 1334 XCTAssertNotNil(dict); 1335 1336 GPBStringInt64Dictionary *dict2 = 1337 [[GPBStringInt64Dictionary alloc] initWithDictionary:dict]; 1338 XCTAssertNotNil(dict2); 1339 1340 // Should be new pointer, but equal objects. 1341 XCTAssertNotEqual(dict, dict2); 1342 XCTAssertEqualObjects(dict, dict2); 1343 [dict2 release]; 1344 [dict release]; 1345} 1346 1347- (void)testAdds { 1348 GPBStringInt64Dictionary *dict = [[GPBStringInt64Dictionary alloc] init]; 1349 XCTAssertNotNil(dict); 1350 1351 XCTAssertEqual(dict.count, 0U); 1352 [dict setInt64:400 forKey:@"foo"]; 1353 XCTAssertEqual(dict.count, 1U); 1354 1355 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 1356 const int64_t kValues[] = { 401, 402, 403 }; 1357 GPBStringInt64Dictionary *dict2 = 1358 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues 1359 forKeys:kKeys 1360 count:GPBARRAYSIZE(kValues)]; 1361 XCTAssertNotNil(dict2); 1362 [dict addEntriesFromDictionary:dict2]; 1363 XCTAssertEqual(dict.count, 4U); 1364 1365 int64_t value; 1366 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1367 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1368 XCTAssertEqual(value, 400); 1369 XCTAssertTrue([dict getInt64:NULL forKey:@"bar"]); 1370 XCTAssertTrue([dict getInt64:&value forKey:@"bar"]); 1371 XCTAssertEqual(value, 401); 1372 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1373 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1374 XCTAssertEqual(value, 402); 1375 XCTAssertTrue([dict getInt64:NULL forKey:@"mumble"]); 1376 XCTAssertTrue([dict getInt64:&value forKey:@"mumble"]); 1377 XCTAssertEqual(value, 403); 1378 [dict2 release]; 1379 [dict release]; 1380} 1381 1382- (void)testRemove { 1383 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1384 const int64_t kValues[] = { 400, 401, 402, 403 }; 1385 GPBStringInt64Dictionary *dict = 1386 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues 1387 forKeys:kKeys 1388 count:GPBARRAYSIZE(kValues)]; 1389 XCTAssertNotNil(dict); 1390 XCTAssertEqual(dict.count, 4U); 1391 1392 [dict removeInt64ForKey:@"bar"]; 1393 XCTAssertEqual(dict.count, 3U); 1394 int64_t value; 1395 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1396 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1397 XCTAssertEqual(value, 400); 1398 XCTAssertFalse([dict getInt64:NULL forKey:@"bar"]); 1399 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1400 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1401 XCTAssertEqual(value, 402); 1402 XCTAssertTrue([dict getInt64:NULL forKey:@"mumble"]); 1403 XCTAssertTrue([dict getInt64:&value forKey:@"mumble"]); 1404 XCTAssertEqual(value, 403); 1405 1406 // Remove again does nothing. 1407 [dict removeInt64ForKey:@"bar"]; 1408 XCTAssertEqual(dict.count, 3U); 1409 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1410 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1411 XCTAssertEqual(value, 400); 1412 XCTAssertFalse([dict getInt64:NULL forKey:@"bar"]); 1413 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1414 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1415 XCTAssertEqual(value, 402); 1416 XCTAssertTrue([dict getInt64:NULL forKey:@"mumble"]); 1417 XCTAssertTrue([dict getInt64:&value forKey:@"mumble"]); 1418 XCTAssertEqual(value, 403); 1419 1420 [dict removeInt64ForKey:@"mumble"]; 1421 XCTAssertEqual(dict.count, 2U); 1422 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1423 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1424 XCTAssertEqual(value, 400); 1425 XCTAssertFalse([dict getInt64:NULL forKey:@"bar"]); 1426 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1427 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1428 XCTAssertEqual(value, 402); 1429 XCTAssertFalse([dict getInt64:NULL forKey:@"mumble"]); 1430 1431 [dict removeAll]; 1432 XCTAssertEqual(dict.count, 0U); 1433 XCTAssertFalse([dict getInt64:NULL forKey:@"foo"]); 1434 XCTAssertFalse([dict getInt64:NULL forKey:@"bar"]); 1435 XCTAssertFalse([dict getInt64:NULL forKey:@"baz"]); 1436 XCTAssertFalse([dict getInt64:NULL forKey:@"mumble"]); 1437 [dict release]; 1438} 1439 1440- (void)testInplaceMutation { 1441 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1442 const int64_t kValues[] = { 400, 401, 402, 403 }; 1443 GPBStringInt64Dictionary *dict = 1444 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues 1445 forKeys:kKeys 1446 count:GPBARRAYSIZE(kValues)]; 1447 XCTAssertNotNil(dict); 1448 XCTAssertEqual(dict.count, 4U); 1449 int64_t value; 1450 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1451 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1452 XCTAssertEqual(value, 400); 1453 XCTAssertTrue([dict getInt64:NULL forKey:@"bar"]); 1454 XCTAssertTrue([dict getInt64:&value forKey:@"bar"]); 1455 XCTAssertEqual(value, 401); 1456 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1457 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1458 XCTAssertEqual(value, 402); 1459 XCTAssertTrue([dict getInt64:NULL forKey:@"mumble"]); 1460 XCTAssertTrue([dict getInt64:&value forKey:@"mumble"]); 1461 XCTAssertEqual(value, 403); 1462 1463 [dict setInt64:403 forKey:@"foo"]; 1464 XCTAssertEqual(dict.count, 4U); 1465 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1466 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1467 XCTAssertEqual(value, 403); 1468 XCTAssertTrue([dict getInt64:NULL forKey:@"bar"]); 1469 XCTAssertTrue([dict getInt64:&value forKey:@"bar"]); 1470 XCTAssertEqual(value, 401); 1471 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1472 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1473 XCTAssertEqual(value, 402); 1474 XCTAssertTrue([dict getInt64:NULL forKey:@"mumble"]); 1475 XCTAssertTrue([dict getInt64:&value forKey:@"mumble"]); 1476 XCTAssertEqual(value, 403); 1477 1478 [dict setInt64:401 forKey:@"mumble"]; 1479 XCTAssertEqual(dict.count, 4U); 1480 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1481 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1482 XCTAssertEqual(value, 403); 1483 XCTAssertTrue([dict getInt64:NULL forKey:@"bar"]); 1484 XCTAssertTrue([dict getInt64:&value forKey:@"bar"]); 1485 XCTAssertEqual(value, 401); 1486 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1487 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1488 XCTAssertEqual(value, 402); 1489 XCTAssertTrue([dict getInt64:NULL forKey:@"mumble"]); 1490 XCTAssertTrue([dict getInt64:&value forKey:@"mumble"]); 1491 XCTAssertEqual(value, 401); 1492 1493 const NSString *kKeys2[] = { @"bar", @"baz" }; 1494 const int64_t kValues2[] = { 402, 400 }; 1495 GPBStringInt64Dictionary *dict2 = 1496 [[GPBStringInt64Dictionary alloc] initWithInt64s:kValues2 1497 forKeys:kKeys2 1498 count:GPBARRAYSIZE(kValues2)]; 1499 XCTAssertNotNil(dict2); 1500 [dict addEntriesFromDictionary:dict2]; 1501 XCTAssertEqual(dict.count, 4U); 1502 XCTAssertTrue([dict getInt64:NULL forKey:@"foo"]); 1503 XCTAssertTrue([dict getInt64:&value forKey:@"foo"]); 1504 XCTAssertEqual(value, 403); 1505 XCTAssertTrue([dict getInt64:NULL forKey:@"bar"]); 1506 XCTAssertTrue([dict getInt64:&value forKey:@"bar"]); 1507 XCTAssertEqual(value, 402); 1508 XCTAssertTrue([dict getInt64:NULL forKey:@"baz"]); 1509 XCTAssertTrue([dict getInt64:&value forKey:@"baz"]); 1510 XCTAssertEqual(value, 400); 1511 XCTAssertTrue([dict getInt64:NULL forKey:@"mumble"]); 1512 XCTAssertTrue([dict getInt64:&value forKey:@"mumble"]); 1513 XCTAssertEqual(value, 401); 1514 1515 [dict2 release]; 1516 [dict release]; 1517} 1518 1519@end 1520 1521#pragma mark - String -> Bool 1522 1523@interface GPBStringBoolDictionaryTests : XCTestCase 1524@end 1525 1526@implementation GPBStringBoolDictionaryTests 1527 1528- (void)testEmpty { 1529 GPBStringBoolDictionary *dict = [[GPBStringBoolDictionary alloc] init]; 1530 XCTAssertNotNil(dict); 1531 XCTAssertEqual(dict.count, 0U); 1532 XCTAssertFalse([dict getBool:NULL forKey:@"foo"]); 1533 [dict enumerateKeysAndBoolsUsingBlock:^(NSString *aKey, BOOL aValue, BOOL *stop) { 1534 #pragma unused(aKey, aValue, stop) 1535 XCTFail(@"Shouldn't get here!"); 1536 }]; 1537 [dict release]; 1538} 1539 1540- (void)testOne { 1541 GPBStringBoolDictionary *dict = [[GPBStringBoolDictionary alloc] init]; 1542 [dict setBool:YES forKey:@"foo"]; 1543 XCTAssertNotNil(dict); 1544 XCTAssertEqual(dict.count, 1U); 1545 BOOL value; 1546 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1547 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1548 XCTAssertEqual(value, YES); 1549 XCTAssertFalse([dict getBool:NULL forKey:@"bar"]); 1550 [dict enumerateKeysAndBoolsUsingBlock:^(NSString *aKey, BOOL aValue, BOOL *stop) { 1551 XCTAssertEqualObjects(aKey, @"foo"); 1552 XCTAssertEqual(aValue, YES); 1553 XCTAssertNotEqual(stop, NULL); 1554 }]; 1555 [dict release]; 1556} 1557 1558- (void)testBasics { 1559 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 1560 const BOOL kValues[] = { YES, YES, NO }; 1561 GPBStringBoolDictionary *dict = 1562 [[GPBStringBoolDictionary alloc] initWithBools:kValues 1563 forKeys:kKeys 1564 count:GPBARRAYSIZE(kValues)]; 1565 XCTAssertNotNil(dict); 1566 XCTAssertEqual(dict.count, 3U); 1567 BOOL value; 1568 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1569 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1570 XCTAssertEqual(value, YES); 1571 XCTAssertTrue([dict getBool:NULL forKey:@"bar"]); 1572 XCTAssertTrue([dict getBool:&value forKey:@"bar"]); 1573 XCTAssertEqual(value, YES); 1574 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1575 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1576 XCTAssertEqual(value, NO); 1577 XCTAssertFalse([dict getBool:NULL forKey:@"mumble"]); 1578 1579 __block NSUInteger idx = 0; 1580 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 1581 BOOL *seenValues = malloc(3 * sizeof(BOOL)); 1582 [dict enumerateKeysAndBoolsUsingBlock:^(NSString *aKey, BOOL aValue, BOOL *stop) { 1583 XCTAssertLessThan(idx, 3U); 1584 seenKeys[idx] = aKey; 1585 seenValues[idx] = aValue; 1586 XCTAssertNotEqual(stop, NULL); 1587 ++idx; 1588 }]; 1589 for (int i = 0; i < 3; ++i) { 1590 BOOL foundKey = NO; 1591 for (int j = 0; (j < 3) && !foundKey; ++j) { 1592 if ([kKeys[i] isEqual:seenKeys[j]]) { 1593 foundKey = YES; 1594 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 1595 } 1596 } 1597 XCTAssertTrue(foundKey, @"i = %d", i); 1598 } 1599 free(seenKeys); 1600 free(seenValues); 1601 1602 // Stopping the enumeration. 1603 idx = 0; 1604 [dict enumerateKeysAndBoolsUsingBlock:^(NSString *aKey, BOOL aValue, BOOL *stop) { 1605 #pragma unused(aKey, aValue) 1606 if (idx == 1) *stop = YES; 1607 XCTAssertNotEqual(idx, 2U); 1608 ++idx; 1609 }]; 1610 [dict release]; 1611} 1612 1613- (void)testEquality { 1614 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 1615 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 1616 const BOOL kValues1[] = { YES, YES, NO }; 1617 const BOOL kValues2[] = { YES, NO, NO }; 1618 const BOOL kValues3[] = { YES, YES, NO, NO }; 1619 GPBStringBoolDictionary *dict1 = 1620 [[GPBStringBoolDictionary alloc] initWithBools:kValues1 1621 forKeys:kKeys1 1622 count:GPBARRAYSIZE(kValues1)]; 1623 XCTAssertNotNil(dict1); 1624 GPBStringBoolDictionary *dict1prime = 1625 [[GPBStringBoolDictionary alloc] initWithBools:kValues1 1626 forKeys:kKeys1 1627 count:GPBARRAYSIZE(kValues1)]; 1628 XCTAssertNotNil(dict1prime); 1629 GPBStringBoolDictionary *dict2 = 1630 [[GPBStringBoolDictionary alloc] initWithBools:kValues2 1631 forKeys:kKeys1 1632 count:GPBARRAYSIZE(kValues2)]; 1633 XCTAssertNotNil(dict2); 1634 GPBStringBoolDictionary *dict3 = 1635 [[GPBStringBoolDictionary alloc] initWithBools:kValues1 1636 forKeys:kKeys2 1637 count:GPBARRAYSIZE(kValues1)]; 1638 XCTAssertNotNil(dict3); 1639 GPBStringBoolDictionary *dict4 = 1640 [[GPBStringBoolDictionary alloc] initWithBools:kValues3 1641 forKeys:kKeys1 1642 count:GPBARRAYSIZE(kValues3)]; 1643 XCTAssertNotNil(dict4); 1644 1645 // 1/1Prime should be different objects, but equal. 1646 XCTAssertNotEqual(dict1, dict1prime); 1647 XCTAssertEqualObjects(dict1, dict1prime); 1648 // Equal, so they must have same hash. 1649 XCTAssertEqual([dict1 hash], [dict1prime hash]); 1650 1651 // 2 is same keys, different values; not equal. 1652 XCTAssertNotEqualObjects(dict1, dict2); 1653 1654 // 3 is different keys, same values; not equal. 1655 XCTAssertNotEqualObjects(dict1, dict3); 1656 1657 // 4 extra pair; not equal 1658 XCTAssertNotEqualObjects(dict1, dict4); 1659 1660 [dict1 release]; 1661 [dict1prime release]; 1662 [dict2 release]; 1663 [dict3 release]; 1664 [dict4 release]; 1665} 1666 1667- (void)testCopy { 1668 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1669 const BOOL kValues[] = { YES, YES, NO, NO }; 1670 GPBStringBoolDictionary *dict = 1671 [[GPBStringBoolDictionary alloc] initWithBools:kValues 1672 forKeys:kKeys 1673 count:GPBARRAYSIZE(kValues)]; 1674 XCTAssertNotNil(dict); 1675 1676 GPBStringBoolDictionary *dict2 = [dict copy]; 1677 XCTAssertNotNil(dict2); 1678 1679 // Should be new object but equal. 1680 XCTAssertNotEqual(dict, dict2); 1681 XCTAssertEqualObjects(dict, dict2); 1682 XCTAssertTrue([dict2 isKindOfClass:[GPBStringBoolDictionary class]]); 1683 1684 [dict2 release]; 1685 [dict release]; 1686} 1687 1688- (void)testDictionaryFromDictionary { 1689 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1690 const BOOL kValues[] = { YES, YES, NO, NO }; 1691 GPBStringBoolDictionary *dict = 1692 [[GPBStringBoolDictionary alloc] initWithBools:kValues 1693 forKeys:kKeys 1694 count:GPBARRAYSIZE(kValues)]; 1695 XCTAssertNotNil(dict); 1696 1697 GPBStringBoolDictionary *dict2 = 1698 [[GPBStringBoolDictionary alloc] initWithDictionary:dict]; 1699 XCTAssertNotNil(dict2); 1700 1701 // Should be new pointer, but equal objects. 1702 XCTAssertNotEqual(dict, dict2); 1703 XCTAssertEqualObjects(dict, dict2); 1704 [dict2 release]; 1705 [dict release]; 1706} 1707 1708- (void)testAdds { 1709 GPBStringBoolDictionary *dict = [[GPBStringBoolDictionary alloc] init]; 1710 XCTAssertNotNil(dict); 1711 1712 XCTAssertEqual(dict.count, 0U); 1713 [dict setBool:YES forKey:@"foo"]; 1714 XCTAssertEqual(dict.count, 1U); 1715 1716 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 1717 const BOOL kValues[] = { YES, NO, NO }; 1718 GPBStringBoolDictionary *dict2 = 1719 [[GPBStringBoolDictionary alloc] initWithBools:kValues 1720 forKeys:kKeys 1721 count:GPBARRAYSIZE(kValues)]; 1722 XCTAssertNotNil(dict2); 1723 [dict addEntriesFromDictionary:dict2]; 1724 XCTAssertEqual(dict.count, 4U); 1725 1726 BOOL value; 1727 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1728 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1729 XCTAssertEqual(value, YES); 1730 XCTAssertTrue([dict getBool:NULL forKey:@"bar"]); 1731 XCTAssertTrue([dict getBool:&value forKey:@"bar"]); 1732 XCTAssertEqual(value, YES); 1733 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1734 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1735 XCTAssertEqual(value, NO); 1736 XCTAssertTrue([dict getBool:NULL forKey:@"mumble"]); 1737 XCTAssertTrue([dict getBool:&value forKey:@"mumble"]); 1738 XCTAssertEqual(value, NO); 1739 [dict2 release]; 1740 [dict release]; 1741} 1742 1743- (void)testRemove { 1744 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1745 const BOOL kValues[] = { YES, YES, NO, NO }; 1746 GPBStringBoolDictionary *dict = 1747 [[GPBStringBoolDictionary alloc] initWithBools:kValues 1748 forKeys:kKeys 1749 count:GPBARRAYSIZE(kValues)]; 1750 XCTAssertNotNil(dict); 1751 XCTAssertEqual(dict.count, 4U); 1752 1753 [dict removeBoolForKey:@"bar"]; 1754 XCTAssertEqual(dict.count, 3U); 1755 BOOL value; 1756 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1757 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1758 XCTAssertEqual(value, YES); 1759 XCTAssertFalse([dict getBool:NULL forKey:@"bar"]); 1760 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1761 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1762 XCTAssertEqual(value, NO); 1763 XCTAssertTrue([dict getBool:NULL forKey:@"mumble"]); 1764 XCTAssertTrue([dict getBool:&value forKey:@"mumble"]); 1765 XCTAssertEqual(value, NO); 1766 1767 // Remove again does nothing. 1768 [dict removeBoolForKey:@"bar"]; 1769 XCTAssertEqual(dict.count, 3U); 1770 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1771 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1772 XCTAssertEqual(value, YES); 1773 XCTAssertFalse([dict getBool:NULL forKey:@"bar"]); 1774 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1775 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1776 XCTAssertEqual(value, NO); 1777 XCTAssertTrue([dict getBool:NULL forKey:@"mumble"]); 1778 XCTAssertTrue([dict getBool:&value forKey:@"mumble"]); 1779 XCTAssertEqual(value, NO); 1780 1781 [dict removeBoolForKey:@"mumble"]; 1782 XCTAssertEqual(dict.count, 2U); 1783 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1784 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1785 XCTAssertEqual(value, YES); 1786 XCTAssertFalse([dict getBool:NULL forKey:@"bar"]); 1787 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1788 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1789 XCTAssertEqual(value, NO); 1790 XCTAssertFalse([dict getBool:NULL forKey:@"mumble"]); 1791 1792 [dict removeAll]; 1793 XCTAssertEqual(dict.count, 0U); 1794 XCTAssertFalse([dict getBool:NULL forKey:@"foo"]); 1795 XCTAssertFalse([dict getBool:NULL forKey:@"bar"]); 1796 XCTAssertFalse([dict getBool:NULL forKey:@"baz"]); 1797 XCTAssertFalse([dict getBool:NULL forKey:@"mumble"]); 1798 [dict release]; 1799} 1800 1801- (void)testInplaceMutation { 1802 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 1803 const BOOL kValues[] = { YES, YES, NO, NO }; 1804 GPBStringBoolDictionary *dict = 1805 [[GPBStringBoolDictionary alloc] initWithBools:kValues 1806 forKeys:kKeys 1807 count:GPBARRAYSIZE(kValues)]; 1808 XCTAssertNotNil(dict); 1809 XCTAssertEqual(dict.count, 4U); 1810 BOOL value; 1811 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1812 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1813 XCTAssertEqual(value, YES); 1814 XCTAssertTrue([dict getBool:NULL forKey:@"bar"]); 1815 XCTAssertTrue([dict getBool:&value forKey:@"bar"]); 1816 XCTAssertEqual(value, YES); 1817 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1818 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1819 XCTAssertEqual(value, NO); 1820 XCTAssertTrue([dict getBool:NULL forKey:@"mumble"]); 1821 XCTAssertTrue([dict getBool:&value forKey:@"mumble"]); 1822 XCTAssertEqual(value, NO); 1823 1824 [dict setBool:NO forKey:@"foo"]; 1825 XCTAssertEqual(dict.count, 4U); 1826 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1827 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1828 XCTAssertEqual(value, NO); 1829 XCTAssertTrue([dict getBool:NULL forKey:@"bar"]); 1830 XCTAssertTrue([dict getBool:&value forKey:@"bar"]); 1831 XCTAssertEqual(value, YES); 1832 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1833 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1834 XCTAssertEqual(value, NO); 1835 XCTAssertTrue([dict getBool:NULL forKey:@"mumble"]); 1836 XCTAssertTrue([dict getBool:&value forKey:@"mumble"]); 1837 XCTAssertEqual(value, NO); 1838 1839 [dict setBool:YES forKey:@"mumble"]; 1840 XCTAssertEqual(dict.count, 4U); 1841 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1842 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1843 XCTAssertEqual(value, NO); 1844 XCTAssertTrue([dict getBool:NULL forKey:@"bar"]); 1845 XCTAssertTrue([dict getBool:&value forKey:@"bar"]); 1846 XCTAssertEqual(value, YES); 1847 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1848 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1849 XCTAssertEqual(value, NO); 1850 XCTAssertTrue([dict getBool:NULL forKey:@"mumble"]); 1851 XCTAssertTrue([dict getBool:&value forKey:@"mumble"]); 1852 XCTAssertEqual(value, YES); 1853 1854 const NSString *kKeys2[] = { @"bar", @"baz" }; 1855 const BOOL kValues2[] = { NO, YES }; 1856 GPBStringBoolDictionary *dict2 = 1857 [[GPBStringBoolDictionary alloc] initWithBools:kValues2 1858 forKeys:kKeys2 1859 count:GPBARRAYSIZE(kValues2)]; 1860 XCTAssertNotNil(dict2); 1861 [dict addEntriesFromDictionary:dict2]; 1862 XCTAssertEqual(dict.count, 4U); 1863 XCTAssertTrue([dict getBool:NULL forKey:@"foo"]); 1864 XCTAssertTrue([dict getBool:&value forKey:@"foo"]); 1865 XCTAssertEqual(value, NO); 1866 XCTAssertTrue([dict getBool:NULL forKey:@"bar"]); 1867 XCTAssertTrue([dict getBool:&value forKey:@"bar"]); 1868 XCTAssertEqual(value, NO); 1869 XCTAssertTrue([dict getBool:NULL forKey:@"baz"]); 1870 XCTAssertTrue([dict getBool:&value forKey:@"baz"]); 1871 XCTAssertEqual(value, YES); 1872 XCTAssertTrue([dict getBool:NULL forKey:@"mumble"]); 1873 XCTAssertTrue([dict getBool:&value forKey:@"mumble"]); 1874 XCTAssertEqual(value, YES); 1875 1876 [dict2 release]; 1877 [dict release]; 1878} 1879 1880@end 1881 1882#pragma mark - String -> Float 1883 1884@interface GPBStringFloatDictionaryTests : XCTestCase 1885@end 1886 1887@implementation GPBStringFloatDictionaryTests 1888 1889- (void)testEmpty { 1890 GPBStringFloatDictionary *dict = [[GPBStringFloatDictionary alloc] init]; 1891 XCTAssertNotNil(dict); 1892 XCTAssertEqual(dict.count, 0U); 1893 XCTAssertFalse([dict getFloat:NULL forKey:@"foo"]); 1894 [dict enumerateKeysAndFloatsUsingBlock:^(NSString *aKey, float aValue, BOOL *stop) { 1895 #pragma unused(aKey, aValue, stop) 1896 XCTFail(@"Shouldn't get here!"); 1897 }]; 1898 [dict release]; 1899} 1900 1901- (void)testOne { 1902 GPBStringFloatDictionary *dict = [[GPBStringFloatDictionary alloc] init]; 1903 [dict setFloat:500.f forKey:@"foo"]; 1904 XCTAssertNotNil(dict); 1905 XCTAssertEqual(dict.count, 1U); 1906 float value; 1907 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 1908 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 1909 XCTAssertEqual(value, 500.f); 1910 XCTAssertFalse([dict getFloat:NULL forKey:@"bar"]); 1911 [dict enumerateKeysAndFloatsUsingBlock:^(NSString *aKey, float aValue, BOOL *stop) { 1912 XCTAssertEqualObjects(aKey, @"foo"); 1913 XCTAssertEqual(aValue, 500.f); 1914 XCTAssertNotEqual(stop, NULL); 1915 }]; 1916 [dict release]; 1917} 1918 1919- (void)testBasics { 1920 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 1921 const float kValues[] = { 500.f, 501.f, 502.f }; 1922 GPBStringFloatDictionary *dict = 1923 [[GPBStringFloatDictionary alloc] initWithFloats:kValues 1924 forKeys:kKeys 1925 count:GPBARRAYSIZE(kValues)]; 1926 XCTAssertNotNil(dict); 1927 XCTAssertEqual(dict.count, 3U); 1928 float value; 1929 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 1930 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 1931 XCTAssertEqual(value, 500.f); 1932 XCTAssertTrue([dict getFloat:NULL forKey:@"bar"]); 1933 XCTAssertTrue([dict getFloat:&value forKey:@"bar"]); 1934 XCTAssertEqual(value, 501.f); 1935 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 1936 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 1937 XCTAssertEqual(value, 502.f); 1938 XCTAssertFalse([dict getFloat:NULL forKey:@"mumble"]); 1939 1940 __block NSUInteger idx = 0; 1941 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 1942 float *seenValues = malloc(3 * sizeof(float)); 1943 [dict enumerateKeysAndFloatsUsingBlock:^(NSString *aKey, float aValue, BOOL *stop) { 1944 XCTAssertLessThan(idx, 3U); 1945 seenKeys[idx] = aKey; 1946 seenValues[idx] = aValue; 1947 XCTAssertNotEqual(stop, NULL); 1948 ++idx; 1949 }]; 1950 for (int i = 0; i < 3; ++i) { 1951 BOOL foundKey = NO; 1952 for (int j = 0; (j < 3) && !foundKey; ++j) { 1953 if ([kKeys[i] isEqual:seenKeys[j]]) { 1954 foundKey = YES; 1955 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 1956 } 1957 } 1958 XCTAssertTrue(foundKey, @"i = %d", i); 1959 } 1960 free(seenKeys); 1961 free(seenValues); 1962 1963 // Stopping the enumeration. 1964 idx = 0; 1965 [dict enumerateKeysAndFloatsUsingBlock:^(NSString *aKey, float aValue, BOOL *stop) { 1966 #pragma unused(aKey, aValue) 1967 if (idx == 1) *stop = YES; 1968 XCTAssertNotEqual(idx, 2U); 1969 ++idx; 1970 }]; 1971 [dict release]; 1972} 1973 1974- (void)testEquality { 1975 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 1976 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 1977 const float kValues1[] = { 500.f, 501.f, 502.f }; 1978 const float kValues2[] = { 500.f, 503.f, 502.f }; 1979 const float kValues3[] = { 500.f, 501.f, 502.f, 503.f }; 1980 GPBStringFloatDictionary *dict1 = 1981 [[GPBStringFloatDictionary alloc] initWithFloats:kValues1 1982 forKeys:kKeys1 1983 count:GPBARRAYSIZE(kValues1)]; 1984 XCTAssertNotNil(dict1); 1985 GPBStringFloatDictionary *dict1prime = 1986 [[GPBStringFloatDictionary alloc] initWithFloats:kValues1 1987 forKeys:kKeys1 1988 count:GPBARRAYSIZE(kValues1)]; 1989 XCTAssertNotNil(dict1prime); 1990 GPBStringFloatDictionary *dict2 = 1991 [[GPBStringFloatDictionary alloc] initWithFloats:kValues2 1992 forKeys:kKeys1 1993 count:GPBARRAYSIZE(kValues2)]; 1994 XCTAssertNotNil(dict2); 1995 GPBStringFloatDictionary *dict3 = 1996 [[GPBStringFloatDictionary alloc] initWithFloats:kValues1 1997 forKeys:kKeys2 1998 count:GPBARRAYSIZE(kValues1)]; 1999 XCTAssertNotNil(dict3); 2000 GPBStringFloatDictionary *dict4 = 2001 [[GPBStringFloatDictionary alloc] initWithFloats:kValues3 2002 forKeys:kKeys1 2003 count:GPBARRAYSIZE(kValues3)]; 2004 XCTAssertNotNil(dict4); 2005 2006 // 1/1Prime should be different objects, but equal. 2007 XCTAssertNotEqual(dict1, dict1prime); 2008 XCTAssertEqualObjects(dict1, dict1prime); 2009 // Equal, so they must have same hash. 2010 XCTAssertEqual([dict1 hash], [dict1prime hash]); 2011 2012 // 2 is same keys, different values; not equal. 2013 XCTAssertNotEqualObjects(dict1, dict2); 2014 2015 // 3 is different keys, same values; not equal. 2016 XCTAssertNotEqualObjects(dict1, dict3); 2017 2018 // 4 extra pair; not equal 2019 XCTAssertNotEqualObjects(dict1, dict4); 2020 2021 [dict1 release]; 2022 [dict1prime release]; 2023 [dict2 release]; 2024 [dict3 release]; 2025 [dict4 release]; 2026} 2027 2028- (void)testCopy { 2029 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2030 const float kValues[] = { 500.f, 501.f, 502.f, 503.f }; 2031 GPBStringFloatDictionary *dict = 2032 [[GPBStringFloatDictionary alloc] initWithFloats:kValues 2033 forKeys:kKeys 2034 count:GPBARRAYSIZE(kValues)]; 2035 XCTAssertNotNil(dict); 2036 2037 GPBStringFloatDictionary *dict2 = [dict copy]; 2038 XCTAssertNotNil(dict2); 2039 2040 // Should be new object but equal. 2041 XCTAssertNotEqual(dict, dict2); 2042 XCTAssertEqualObjects(dict, dict2); 2043 XCTAssertTrue([dict2 isKindOfClass:[GPBStringFloatDictionary class]]); 2044 2045 [dict2 release]; 2046 [dict release]; 2047} 2048 2049- (void)testDictionaryFromDictionary { 2050 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2051 const float kValues[] = { 500.f, 501.f, 502.f, 503.f }; 2052 GPBStringFloatDictionary *dict = 2053 [[GPBStringFloatDictionary alloc] initWithFloats:kValues 2054 forKeys:kKeys 2055 count:GPBARRAYSIZE(kValues)]; 2056 XCTAssertNotNil(dict); 2057 2058 GPBStringFloatDictionary *dict2 = 2059 [[GPBStringFloatDictionary alloc] initWithDictionary:dict]; 2060 XCTAssertNotNil(dict2); 2061 2062 // Should be new pointer, but equal objects. 2063 XCTAssertNotEqual(dict, dict2); 2064 XCTAssertEqualObjects(dict, dict2); 2065 [dict2 release]; 2066 [dict release]; 2067} 2068 2069- (void)testAdds { 2070 GPBStringFloatDictionary *dict = [[GPBStringFloatDictionary alloc] init]; 2071 XCTAssertNotNil(dict); 2072 2073 XCTAssertEqual(dict.count, 0U); 2074 [dict setFloat:500.f forKey:@"foo"]; 2075 XCTAssertEqual(dict.count, 1U); 2076 2077 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 2078 const float kValues[] = { 501.f, 502.f, 503.f }; 2079 GPBStringFloatDictionary *dict2 = 2080 [[GPBStringFloatDictionary alloc] initWithFloats:kValues 2081 forKeys:kKeys 2082 count:GPBARRAYSIZE(kValues)]; 2083 XCTAssertNotNil(dict2); 2084 [dict addEntriesFromDictionary:dict2]; 2085 XCTAssertEqual(dict.count, 4U); 2086 2087 float value; 2088 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2089 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2090 XCTAssertEqual(value, 500.f); 2091 XCTAssertTrue([dict getFloat:NULL forKey:@"bar"]); 2092 XCTAssertTrue([dict getFloat:&value forKey:@"bar"]); 2093 XCTAssertEqual(value, 501.f); 2094 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2095 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2096 XCTAssertEqual(value, 502.f); 2097 XCTAssertTrue([dict getFloat:NULL forKey:@"mumble"]); 2098 XCTAssertTrue([dict getFloat:&value forKey:@"mumble"]); 2099 XCTAssertEqual(value, 503.f); 2100 [dict2 release]; 2101 [dict release]; 2102} 2103 2104- (void)testRemove { 2105 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2106 const float kValues[] = { 500.f, 501.f, 502.f, 503.f }; 2107 GPBStringFloatDictionary *dict = 2108 [[GPBStringFloatDictionary alloc] initWithFloats:kValues 2109 forKeys:kKeys 2110 count:GPBARRAYSIZE(kValues)]; 2111 XCTAssertNotNil(dict); 2112 XCTAssertEqual(dict.count, 4U); 2113 2114 [dict removeFloatForKey:@"bar"]; 2115 XCTAssertEqual(dict.count, 3U); 2116 float value; 2117 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2118 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2119 XCTAssertEqual(value, 500.f); 2120 XCTAssertFalse([dict getFloat:NULL forKey:@"bar"]); 2121 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2122 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2123 XCTAssertEqual(value, 502.f); 2124 XCTAssertTrue([dict getFloat:NULL forKey:@"mumble"]); 2125 XCTAssertTrue([dict getFloat:&value forKey:@"mumble"]); 2126 XCTAssertEqual(value, 503.f); 2127 2128 // Remove again does nothing. 2129 [dict removeFloatForKey:@"bar"]; 2130 XCTAssertEqual(dict.count, 3U); 2131 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2132 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2133 XCTAssertEqual(value, 500.f); 2134 XCTAssertFalse([dict getFloat:NULL forKey:@"bar"]); 2135 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2136 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2137 XCTAssertEqual(value, 502.f); 2138 XCTAssertTrue([dict getFloat:NULL forKey:@"mumble"]); 2139 XCTAssertTrue([dict getFloat:&value forKey:@"mumble"]); 2140 XCTAssertEqual(value, 503.f); 2141 2142 [dict removeFloatForKey:@"mumble"]; 2143 XCTAssertEqual(dict.count, 2U); 2144 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2145 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2146 XCTAssertEqual(value, 500.f); 2147 XCTAssertFalse([dict getFloat:NULL forKey:@"bar"]); 2148 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2149 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2150 XCTAssertEqual(value, 502.f); 2151 XCTAssertFalse([dict getFloat:NULL forKey:@"mumble"]); 2152 2153 [dict removeAll]; 2154 XCTAssertEqual(dict.count, 0U); 2155 XCTAssertFalse([dict getFloat:NULL forKey:@"foo"]); 2156 XCTAssertFalse([dict getFloat:NULL forKey:@"bar"]); 2157 XCTAssertFalse([dict getFloat:NULL forKey:@"baz"]); 2158 XCTAssertFalse([dict getFloat:NULL forKey:@"mumble"]); 2159 [dict release]; 2160} 2161 2162- (void)testInplaceMutation { 2163 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2164 const float kValues[] = { 500.f, 501.f, 502.f, 503.f }; 2165 GPBStringFloatDictionary *dict = 2166 [[GPBStringFloatDictionary alloc] initWithFloats:kValues 2167 forKeys:kKeys 2168 count:GPBARRAYSIZE(kValues)]; 2169 XCTAssertNotNil(dict); 2170 XCTAssertEqual(dict.count, 4U); 2171 float value; 2172 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2173 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2174 XCTAssertEqual(value, 500.f); 2175 XCTAssertTrue([dict getFloat:NULL forKey:@"bar"]); 2176 XCTAssertTrue([dict getFloat:&value forKey:@"bar"]); 2177 XCTAssertEqual(value, 501.f); 2178 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2179 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2180 XCTAssertEqual(value, 502.f); 2181 XCTAssertTrue([dict getFloat:NULL forKey:@"mumble"]); 2182 XCTAssertTrue([dict getFloat:&value forKey:@"mumble"]); 2183 XCTAssertEqual(value, 503.f); 2184 2185 [dict setFloat:503.f forKey:@"foo"]; 2186 XCTAssertEqual(dict.count, 4U); 2187 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2188 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2189 XCTAssertEqual(value, 503.f); 2190 XCTAssertTrue([dict getFloat:NULL forKey:@"bar"]); 2191 XCTAssertTrue([dict getFloat:&value forKey:@"bar"]); 2192 XCTAssertEqual(value, 501.f); 2193 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2194 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2195 XCTAssertEqual(value, 502.f); 2196 XCTAssertTrue([dict getFloat:NULL forKey:@"mumble"]); 2197 XCTAssertTrue([dict getFloat:&value forKey:@"mumble"]); 2198 XCTAssertEqual(value, 503.f); 2199 2200 [dict setFloat:501.f forKey:@"mumble"]; 2201 XCTAssertEqual(dict.count, 4U); 2202 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2203 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2204 XCTAssertEqual(value, 503.f); 2205 XCTAssertTrue([dict getFloat:NULL forKey:@"bar"]); 2206 XCTAssertTrue([dict getFloat:&value forKey:@"bar"]); 2207 XCTAssertEqual(value, 501.f); 2208 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2209 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2210 XCTAssertEqual(value, 502.f); 2211 XCTAssertTrue([dict getFloat:NULL forKey:@"mumble"]); 2212 XCTAssertTrue([dict getFloat:&value forKey:@"mumble"]); 2213 XCTAssertEqual(value, 501.f); 2214 2215 const NSString *kKeys2[] = { @"bar", @"baz" }; 2216 const float kValues2[] = { 502.f, 500.f }; 2217 GPBStringFloatDictionary *dict2 = 2218 [[GPBStringFloatDictionary alloc] initWithFloats:kValues2 2219 forKeys:kKeys2 2220 count:GPBARRAYSIZE(kValues2)]; 2221 XCTAssertNotNil(dict2); 2222 [dict addEntriesFromDictionary:dict2]; 2223 XCTAssertEqual(dict.count, 4U); 2224 XCTAssertTrue([dict getFloat:NULL forKey:@"foo"]); 2225 XCTAssertTrue([dict getFloat:&value forKey:@"foo"]); 2226 XCTAssertEqual(value, 503.f); 2227 XCTAssertTrue([dict getFloat:NULL forKey:@"bar"]); 2228 XCTAssertTrue([dict getFloat:&value forKey:@"bar"]); 2229 XCTAssertEqual(value, 502.f); 2230 XCTAssertTrue([dict getFloat:NULL forKey:@"baz"]); 2231 XCTAssertTrue([dict getFloat:&value forKey:@"baz"]); 2232 XCTAssertEqual(value, 500.f); 2233 XCTAssertTrue([dict getFloat:NULL forKey:@"mumble"]); 2234 XCTAssertTrue([dict getFloat:&value forKey:@"mumble"]); 2235 XCTAssertEqual(value, 501.f); 2236 2237 [dict2 release]; 2238 [dict release]; 2239} 2240 2241@end 2242 2243#pragma mark - String -> Double 2244 2245@interface GPBStringDoubleDictionaryTests : XCTestCase 2246@end 2247 2248@implementation GPBStringDoubleDictionaryTests 2249 2250- (void)testEmpty { 2251 GPBStringDoubleDictionary *dict = [[GPBStringDoubleDictionary alloc] init]; 2252 XCTAssertNotNil(dict); 2253 XCTAssertEqual(dict.count, 0U); 2254 XCTAssertFalse([dict getDouble:NULL forKey:@"foo"]); 2255 [dict enumerateKeysAndDoublesUsingBlock:^(NSString *aKey, double aValue, BOOL *stop) { 2256 #pragma unused(aKey, aValue, stop) 2257 XCTFail(@"Shouldn't get here!"); 2258 }]; 2259 [dict release]; 2260} 2261 2262- (void)testOne { 2263 GPBStringDoubleDictionary *dict = [[GPBStringDoubleDictionary alloc] init]; 2264 [dict setDouble:600. forKey:@"foo"]; 2265 XCTAssertNotNil(dict); 2266 XCTAssertEqual(dict.count, 1U); 2267 double value; 2268 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2269 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2270 XCTAssertEqual(value, 600.); 2271 XCTAssertFalse([dict getDouble:NULL forKey:@"bar"]); 2272 [dict enumerateKeysAndDoublesUsingBlock:^(NSString *aKey, double aValue, BOOL *stop) { 2273 XCTAssertEqualObjects(aKey, @"foo"); 2274 XCTAssertEqual(aValue, 600.); 2275 XCTAssertNotEqual(stop, NULL); 2276 }]; 2277 [dict release]; 2278} 2279 2280- (void)testBasics { 2281 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 2282 const double kValues[] = { 600., 601., 602. }; 2283 GPBStringDoubleDictionary *dict = 2284 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues 2285 forKeys:kKeys 2286 count:GPBARRAYSIZE(kValues)]; 2287 XCTAssertNotNil(dict); 2288 XCTAssertEqual(dict.count, 3U); 2289 double value; 2290 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2291 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2292 XCTAssertEqual(value, 600.); 2293 XCTAssertTrue([dict getDouble:NULL forKey:@"bar"]); 2294 XCTAssertTrue([dict getDouble:&value forKey:@"bar"]); 2295 XCTAssertEqual(value, 601.); 2296 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2297 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2298 XCTAssertEqual(value, 602.); 2299 XCTAssertFalse([dict getDouble:NULL forKey:@"mumble"]); 2300 2301 __block NSUInteger idx = 0; 2302 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 2303 double *seenValues = malloc(3 * sizeof(double)); 2304 [dict enumerateKeysAndDoublesUsingBlock:^(NSString *aKey, double aValue, BOOL *stop) { 2305 XCTAssertLessThan(idx, 3U); 2306 seenKeys[idx] = aKey; 2307 seenValues[idx] = aValue; 2308 XCTAssertNotEqual(stop, NULL); 2309 ++idx; 2310 }]; 2311 for (int i = 0; i < 3; ++i) { 2312 BOOL foundKey = NO; 2313 for (int j = 0; (j < 3) && !foundKey; ++j) { 2314 if ([kKeys[i] isEqual:seenKeys[j]]) { 2315 foundKey = YES; 2316 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 2317 } 2318 } 2319 XCTAssertTrue(foundKey, @"i = %d", i); 2320 } 2321 free(seenKeys); 2322 free(seenValues); 2323 2324 // Stopping the enumeration. 2325 idx = 0; 2326 [dict enumerateKeysAndDoublesUsingBlock:^(NSString *aKey, double aValue, BOOL *stop) { 2327 #pragma unused(aKey, aValue) 2328 if (idx == 1) *stop = YES; 2329 XCTAssertNotEqual(idx, 2U); 2330 ++idx; 2331 }]; 2332 [dict release]; 2333} 2334 2335- (void)testEquality { 2336 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 2337 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 2338 const double kValues1[] = { 600., 601., 602. }; 2339 const double kValues2[] = { 600., 603., 602. }; 2340 const double kValues3[] = { 600., 601., 602., 603. }; 2341 GPBStringDoubleDictionary *dict1 = 2342 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues1 2343 forKeys:kKeys1 2344 count:GPBARRAYSIZE(kValues1)]; 2345 XCTAssertNotNil(dict1); 2346 GPBStringDoubleDictionary *dict1prime = 2347 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues1 2348 forKeys:kKeys1 2349 count:GPBARRAYSIZE(kValues1)]; 2350 XCTAssertNotNil(dict1prime); 2351 GPBStringDoubleDictionary *dict2 = 2352 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues2 2353 forKeys:kKeys1 2354 count:GPBARRAYSIZE(kValues2)]; 2355 XCTAssertNotNil(dict2); 2356 GPBStringDoubleDictionary *dict3 = 2357 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues1 2358 forKeys:kKeys2 2359 count:GPBARRAYSIZE(kValues1)]; 2360 XCTAssertNotNil(dict3); 2361 GPBStringDoubleDictionary *dict4 = 2362 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues3 2363 forKeys:kKeys1 2364 count:GPBARRAYSIZE(kValues3)]; 2365 XCTAssertNotNil(dict4); 2366 2367 // 1/1Prime should be different objects, but equal. 2368 XCTAssertNotEqual(dict1, dict1prime); 2369 XCTAssertEqualObjects(dict1, dict1prime); 2370 // Equal, so they must have same hash. 2371 XCTAssertEqual([dict1 hash], [dict1prime hash]); 2372 2373 // 2 is same keys, different values; not equal. 2374 XCTAssertNotEqualObjects(dict1, dict2); 2375 2376 // 3 is different keys, same values; not equal. 2377 XCTAssertNotEqualObjects(dict1, dict3); 2378 2379 // 4 extra pair; not equal 2380 XCTAssertNotEqualObjects(dict1, dict4); 2381 2382 [dict1 release]; 2383 [dict1prime release]; 2384 [dict2 release]; 2385 [dict3 release]; 2386 [dict4 release]; 2387} 2388 2389- (void)testCopy { 2390 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2391 const double kValues[] = { 600., 601., 602., 603. }; 2392 GPBStringDoubleDictionary *dict = 2393 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues 2394 forKeys:kKeys 2395 count:GPBARRAYSIZE(kValues)]; 2396 XCTAssertNotNil(dict); 2397 2398 GPBStringDoubleDictionary *dict2 = [dict copy]; 2399 XCTAssertNotNil(dict2); 2400 2401 // Should be new object but equal. 2402 XCTAssertNotEqual(dict, dict2); 2403 XCTAssertEqualObjects(dict, dict2); 2404 XCTAssertTrue([dict2 isKindOfClass:[GPBStringDoubleDictionary class]]); 2405 2406 [dict2 release]; 2407 [dict release]; 2408} 2409 2410- (void)testDictionaryFromDictionary { 2411 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2412 const double kValues[] = { 600., 601., 602., 603. }; 2413 GPBStringDoubleDictionary *dict = 2414 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues 2415 forKeys:kKeys 2416 count:GPBARRAYSIZE(kValues)]; 2417 XCTAssertNotNil(dict); 2418 2419 GPBStringDoubleDictionary *dict2 = 2420 [[GPBStringDoubleDictionary alloc] initWithDictionary:dict]; 2421 XCTAssertNotNil(dict2); 2422 2423 // Should be new pointer, but equal objects. 2424 XCTAssertNotEqual(dict, dict2); 2425 XCTAssertEqualObjects(dict, dict2); 2426 [dict2 release]; 2427 [dict release]; 2428} 2429 2430- (void)testAdds { 2431 GPBStringDoubleDictionary *dict = [[GPBStringDoubleDictionary alloc] init]; 2432 XCTAssertNotNil(dict); 2433 2434 XCTAssertEqual(dict.count, 0U); 2435 [dict setDouble:600. forKey:@"foo"]; 2436 XCTAssertEqual(dict.count, 1U); 2437 2438 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 2439 const double kValues[] = { 601., 602., 603. }; 2440 GPBStringDoubleDictionary *dict2 = 2441 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues 2442 forKeys:kKeys 2443 count:GPBARRAYSIZE(kValues)]; 2444 XCTAssertNotNil(dict2); 2445 [dict addEntriesFromDictionary:dict2]; 2446 XCTAssertEqual(dict.count, 4U); 2447 2448 double value; 2449 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2450 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2451 XCTAssertEqual(value, 600.); 2452 XCTAssertTrue([dict getDouble:NULL forKey:@"bar"]); 2453 XCTAssertTrue([dict getDouble:&value forKey:@"bar"]); 2454 XCTAssertEqual(value, 601.); 2455 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2456 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2457 XCTAssertEqual(value, 602.); 2458 XCTAssertTrue([dict getDouble:NULL forKey:@"mumble"]); 2459 XCTAssertTrue([dict getDouble:&value forKey:@"mumble"]); 2460 XCTAssertEqual(value, 603.); 2461 [dict2 release]; 2462 [dict release]; 2463} 2464 2465- (void)testRemove { 2466 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2467 const double kValues[] = { 600., 601., 602., 603. }; 2468 GPBStringDoubleDictionary *dict = 2469 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues 2470 forKeys:kKeys 2471 count:GPBARRAYSIZE(kValues)]; 2472 XCTAssertNotNil(dict); 2473 XCTAssertEqual(dict.count, 4U); 2474 2475 [dict removeDoubleForKey:@"bar"]; 2476 XCTAssertEqual(dict.count, 3U); 2477 double value; 2478 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2479 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2480 XCTAssertEqual(value, 600.); 2481 XCTAssertFalse([dict getDouble:NULL forKey:@"bar"]); 2482 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2483 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2484 XCTAssertEqual(value, 602.); 2485 XCTAssertTrue([dict getDouble:NULL forKey:@"mumble"]); 2486 XCTAssertTrue([dict getDouble:&value forKey:@"mumble"]); 2487 XCTAssertEqual(value, 603.); 2488 2489 // Remove again does nothing. 2490 [dict removeDoubleForKey:@"bar"]; 2491 XCTAssertEqual(dict.count, 3U); 2492 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2493 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2494 XCTAssertEqual(value, 600.); 2495 XCTAssertFalse([dict getDouble:NULL forKey:@"bar"]); 2496 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2497 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2498 XCTAssertEqual(value, 602.); 2499 XCTAssertTrue([dict getDouble:NULL forKey:@"mumble"]); 2500 XCTAssertTrue([dict getDouble:&value forKey:@"mumble"]); 2501 XCTAssertEqual(value, 603.); 2502 2503 [dict removeDoubleForKey:@"mumble"]; 2504 XCTAssertEqual(dict.count, 2U); 2505 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2506 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2507 XCTAssertEqual(value, 600.); 2508 XCTAssertFalse([dict getDouble:NULL forKey:@"bar"]); 2509 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2510 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2511 XCTAssertEqual(value, 602.); 2512 XCTAssertFalse([dict getDouble:NULL forKey:@"mumble"]); 2513 2514 [dict removeAll]; 2515 XCTAssertEqual(dict.count, 0U); 2516 XCTAssertFalse([dict getDouble:NULL forKey:@"foo"]); 2517 XCTAssertFalse([dict getDouble:NULL forKey:@"bar"]); 2518 XCTAssertFalse([dict getDouble:NULL forKey:@"baz"]); 2519 XCTAssertFalse([dict getDouble:NULL forKey:@"mumble"]); 2520 [dict release]; 2521} 2522 2523- (void)testInplaceMutation { 2524 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2525 const double kValues[] = { 600., 601., 602., 603. }; 2526 GPBStringDoubleDictionary *dict = 2527 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues 2528 forKeys:kKeys 2529 count:GPBARRAYSIZE(kValues)]; 2530 XCTAssertNotNil(dict); 2531 XCTAssertEqual(dict.count, 4U); 2532 double value; 2533 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2534 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2535 XCTAssertEqual(value, 600.); 2536 XCTAssertTrue([dict getDouble:NULL forKey:@"bar"]); 2537 XCTAssertTrue([dict getDouble:&value forKey:@"bar"]); 2538 XCTAssertEqual(value, 601.); 2539 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2540 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2541 XCTAssertEqual(value, 602.); 2542 XCTAssertTrue([dict getDouble:NULL forKey:@"mumble"]); 2543 XCTAssertTrue([dict getDouble:&value forKey:@"mumble"]); 2544 XCTAssertEqual(value, 603.); 2545 2546 [dict setDouble:603. forKey:@"foo"]; 2547 XCTAssertEqual(dict.count, 4U); 2548 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2549 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2550 XCTAssertEqual(value, 603.); 2551 XCTAssertTrue([dict getDouble:NULL forKey:@"bar"]); 2552 XCTAssertTrue([dict getDouble:&value forKey:@"bar"]); 2553 XCTAssertEqual(value, 601.); 2554 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2555 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2556 XCTAssertEqual(value, 602.); 2557 XCTAssertTrue([dict getDouble:NULL forKey:@"mumble"]); 2558 XCTAssertTrue([dict getDouble:&value forKey:@"mumble"]); 2559 XCTAssertEqual(value, 603.); 2560 2561 [dict setDouble:601. forKey:@"mumble"]; 2562 XCTAssertEqual(dict.count, 4U); 2563 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2564 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2565 XCTAssertEqual(value, 603.); 2566 XCTAssertTrue([dict getDouble:NULL forKey:@"bar"]); 2567 XCTAssertTrue([dict getDouble:&value forKey:@"bar"]); 2568 XCTAssertEqual(value, 601.); 2569 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2570 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2571 XCTAssertEqual(value, 602.); 2572 XCTAssertTrue([dict getDouble:NULL forKey:@"mumble"]); 2573 XCTAssertTrue([dict getDouble:&value forKey:@"mumble"]); 2574 XCTAssertEqual(value, 601.); 2575 2576 const NSString *kKeys2[] = { @"bar", @"baz" }; 2577 const double kValues2[] = { 602., 600. }; 2578 GPBStringDoubleDictionary *dict2 = 2579 [[GPBStringDoubleDictionary alloc] initWithDoubles:kValues2 2580 forKeys:kKeys2 2581 count:GPBARRAYSIZE(kValues2)]; 2582 XCTAssertNotNil(dict2); 2583 [dict addEntriesFromDictionary:dict2]; 2584 XCTAssertEqual(dict.count, 4U); 2585 XCTAssertTrue([dict getDouble:NULL forKey:@"foo"]); 2586 XCTAssertTrue([dict getDouble:&value forKey:@"foo"]); 2587 XCTAssertEqual(value, 603.); 2588 XCTAssertTrue([dict getDouble:NULL forKey:@"bar"]); 2589 XCTAssertTrue([dict getDouble:&value forKey:@"bar"]); 2590 XCTAssertEqual(value, 602.); 2591 XCTAssertTrue([dict getDouble:NULL forKey:@"baz"]); 2592 XCTAssertTrue([dict getDouble:&value forKey:@"baz"]); 2593 XCTAssertEqual(value, 600.); 2594 XCTAssertTrue([dict getDouble:NULL forKey:@"mumble"]); 2595 XCTAssertTrue([dict getDouble:&value forKey:@"mumble"]); 2596 XCTAssertEqual(value, 601.); 2597 2598 [dict2 release]; 2599 [dict release]; 2600} 2601 2602@end 2603 2604#pragma mark - String -> Enum 2605 2606@interface GPBStringEnumDictionaryTests : XCTestCase 2607@end 2608 2609@implementation GPBStringEnumDictionaryTests 2610 2611- (void)testEmpty { 2612 GPBStringEnumDictionary *dict = [[GPBStringEnumDictionary alloc] init]; 2613 XCTAssertNotNil(dict); 2614 XCTAssertEqual(dict.count, 0U); 2615 XCTAssertFalse([dict getEnum:NULL forKey:@"foo"]); 2616 [dict enumerateKeysAndEnumsUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 2617 #pragma unused(aKey, aValue, stop) 2618 XCTFail(@"Shouldn't get here!"); 2619 }]; 2620 [dict release]; 2621} 2622 2623- (void)testOne { 2624 GPBStringEnumDictionary *dict = [[GPBStringEnumDictionary alloc] init]; 2625 [dict setEnum:700 forKey:@"foo"]; 2626 XCTAssertNotNil(dict); 2627 XCTAssertEqual(dict.count, 1U); 2628 int32_t value; 2629 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2630 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2631 XCTAssertEqual(value, 700); 2632 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 2633 [dict enumerateKeysAndEnumsUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 2634 XCTAssertEqualObjects(aKey, @"foo"); 2635 XCTAssertEqual(aValue, 700); 2636 XCTAssertNotEqual(stop, NULL); 2637 }]; 2638 [dict release]; 2639} 2640 2641- (void)testBasics { 2642 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 2643 const int32_t kValues[] = { 700, 701, 702 }; 2644 GPBStringEnumDictionary *dict = 2645 [[GPBStringEnumDictionary alloc] initWithEnums:kValues 2646 forKeys:kKeys 2647 count:GPBARRAYSIZE(kValues)]; 2648 XCTAssertNotNil(dict); 2649 XCTAssertEqual(dict.count, 3U); 2650 int32_t value; 2651 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2652 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2653 XCTAssertEqual(value, 700); 2654 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 2655 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 2656 XCTAssertEqual(value, 701); 2657 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2658 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2659 XCTAssertEqual(value, 702); 2660 XCTAssertFalse([dict getEnum:NULL forKey:@"mumble"]); 2661 2662 __block NSUInteger idx = 0; 2663 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 2664 int32_t *seenValues = malloc(3 * sizeof(int32_t)); 2665 [dict enumerateKeysAndEnumsUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 2666 XCTAssertLessThan(idx, 3U); 2667 seenKeys[idx] = aKey; 2668 seenValues[idx] = aValue; 2669 XCTAssertNotEqual(stop, NULL); 2670 ++idx; 2671 }]; 2672 for (int i = 0; i < 3; ++i) { 2673 BOOL foundKey = NO; 2674 for (int j = 0; (j < 3) && !foundKey; ++j) { 2675 if ([kKeys[i] isEqual:seenKeys[j]]) { 2676 foundKey = YES; 2677 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 2678 } 2679 } 2680 XCTAssertTrue(foundKey, @"i = %d", i); 2681 } 2682 free(seenKeys); 2683 free(seenValues); 2684 2685 // Stopping the enumeration. 2686 idx = 0; 2687 [dict enumerateKeysAndEnumsUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 2688 #pragma unused(aKey, aValue) 2689 if (idx == 1) *stop = YES; 2690 XCTAssertNotEqual(idx, 2U); 2691 ++idx; 2692 }]; 2693 [dict release]; 2694} 2695 2696- (void)testEquality { 2697 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 2698 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 2699 const int32_t kValues1[] = { 700, 701, 702 }; 2700 const int32_t kValues2[] = { 700, 703, 702 }; 2701 const int32_t kValues3[] = { 700, 701, 702, 703 }; 2702 GPBStringEnumDictionary *dict1 = 2703 [[GPBStringEnumDictionary alloc] initWithEnums:kValues1 2704 forKeys:kKeys1 2705 count:GPBARRAYSIZE(kValues1)]; 2706 XCTAssertNotNil(dict1); 2707 GPBStringEnumDictionary *dict1prime = 2708 [[GPBStringEnumDictionary alloc] initWithEnums:kValues1 2709 forKeys:kKeys1 2710 count:GPBARRAYSIZE(kValues1)]; 2711 XCTAssertNotNil(dict1prime); 2712 GPBStringEnumDictionary *dict2 = 2713 [[GPBStringEnumDictionary alloc] initWithEnums:kValues2 2714 forKeys:kKeys1 2715 count:GPBARRAYSIZE(kValues2)]; 2716 XCTAssertNotNil(dict2); 2717 GPBStringEnumDictionary *dict3 = 2718 [[GPBStringEnumDictionary alloc] initWithEnums:kValues1 2719 forKeys:kKeys2 2720 count:GPBARRAYSIZE(kValues1)]; 2721 XCTAssertNotNil(dict3); 2722 GPBStringEnumDictionary *dict4 = 2723 [[GPBStringEnumDictionary alloc] initWithEnums:kValues3 2724 forKeys:kKeys1 2725 count:GPBARRAYSIZE(kValues3)]; 2726 XCTAssertNotNil(dict4); 2727 2728 // 1/1Prime should be different objects, but equal. 2729 XCTAssertNotEqual(dict1, dict1prime); 2730 XCTAssertEqualObjects(dict1, dict1prime); 2731 // Equal, so they must have same hash. 2732 XCTAssertEqual([dict1 hash], [dict1prime hash]); 2733 2734 // 2 is same keys, different values; not equal. 2735 XCTAssertNotEqualObjects(dict1, dict2); 2736 2737 // 3 is different keys, same values; not equal. 2738 XCTAssertNotEqualObjects(dict1, dict3); 2739 2740 // 4 extra pair; not equal 2741 XCTAssertNotEqualObjects(dict1, dict4); 2742 2743 [dict1 release]; 2744 [dict1prime release]; 2745 [dict2 release]; 2746 [dict3 release]; 2747 [dict4 release]; 2748} 2749 2750- (void)testCopy { 2751 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2752 const int32_t kValues[] = { 700, 701, 702, 703 }; 2753 GPBStringEnumDictionary *dict = 2754 [[GPBStringEnumDictionary alloc] initWithEnums:kValues 2755 forKeys:kKeys 2756 count:GPBARRAYSIZE(kValues)]; 2757 XCTAssertNotNil(dict); 2758 2759 GPBStringEnumDictionary *dict2 = [dict copy]; 2760 XCTAssertNotNil(dict2); 2761 2762 // Should be new object but equal. 2763 XCTAssertNotEqual(dict, dict2); 2764 XCTAssertEqualObjects(dict, dict2); 2765 XCTAssertTrue([dict2 isKindOfClass:[GPBStringEnumDictionary class]]); 2766 2767 [dict2 release]; 2768 [dict release]; 2769} 2770 2771- (void)testDictionaryFromDictionary { 2772 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2773 const int32_t kValues[] = { 700, 701, 702, 703 }; 2774 GPBStringEnumDictionary *dict = 2775 [[GPBStringEnumDictionary alloc] initWithEnums:kValues 2776 forKeys:kKeys 2777 count:GPBARRAYSIZE(kValues)]; 2778 XCTAssertNotNil(dict); 2779 2780 GPBStringEnumDictionary *dict2 = 2781 [[GPBStringEnumDictionary alloc] initWithDictionary:dict]; 2782 XCTAssertNotNil(dict2); 2783 2784 // Should be new pointer, but equal objects. 2785 XCTAssertNotEqual(dict, dict2); 2786 XCTAssertEqualObjects(dict, dict2); 2787 [dict2 release]; 2788 [dict release]; 2789} 2790 2791- (void)testAdds { 2792 GPBStringEnumDictionary *dict = [[GPBStringEnumDictionary alloc] init]; 2793 XCTAssertNotNil(dict); 2794 2795 XCTAssertEqual(dict.count, 0U); 2796 [dict setEnum:700 forKey:@"foo"]; 2797 XCTAssertEqual(dict.count, 1U); 2798 2799 const NSString *kKeys[] = { @"bar", @"baz", @"mumble" }; 2800 const int32_t kValues[] = { 701, 702, 703 }; 2801 GPBStringEnumDictionary *dict2 = 2802 [[GPBStringEnumDictionary alloc] initWithEnums:kValues 2803 forKeys:kKeys 2804 count:GPBARRAYSIZE(kValues)]; 2805 XCTAssertNotNil(dict2); 2806 [dict addRawEntriesFromDictionary:dict2]; 2807 XCTAssertEqual(dict.count, 4U); 2808 2809 int32_t value; 2810 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2811 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2812 XCTAssertEqual(value, 700); 2813 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 2814 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 2815 XCTAssertEqual(value, 701); 2816 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2817 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2818 XCTAssertEqual(value, 702); 2819 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 2820 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 2821 XCTAssertEqual(value, 703); 2822 [dict2 release]; 2823 [dict release]; 2824} 2825 2826- (void)testRemove { 2827 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2828 const int32_t kValues[] = { 700, 701, 702, 703 }; 2829 GPBStringEnumDictionary *dict = 2830 [[GPBStringEnumDictionary alloc] initWithEnums:kValues 2831 forKeys:kKeys 2832 count:GPBARRAYSIZE(kValues)]; 2833 XCTAssertNotNil(dict); 2834 XCTAssertEqual(dict.count, 4U); 2835 2836 [dict removeEnumForKey:@"bar"]; 2837 XCTAssertEqual(dict.count, 3U); 2838 int32_t value; 2839 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2840 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2841 XCTAssertEqual(value, 700); 2842 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 2843 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2844 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2845 XCTAssertEqual(value, 702); 2846 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 2847 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 2848 XCTAssertEqual(value, 703); 2849 2850 // Remove again does nothing. 2851 [dict removeEnumForKey:@"bar"]; 2852 XCTAssertEqual(dict.count, 3U); 2853 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2854 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2855 XCTAssertEqual(value, 700); 2856 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 2857 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2858 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2859 XCTAssertEqual(value, 702); 2860 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 2861 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 2862 XCTAssertEqual(value, 703); 2863 2864 [dict removeEnumForKey:@"mumble"]; 2865 XCTAssertEqual(dict.count, 2U); 2866 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2867 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2868 XCTAssertEqual(value, 700); 2869 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 2870 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2871 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2872 XCTAssertEqual(value, 702); 2873 XCTAssertFalse([dict getEnum:NULL forKey:@"mumble"]); 2874 2875 [dict removeAll]; 2876 XCTAssertEqual(dict.count, 0U); 2877 XCTAssertFalse([dict getEnum:NULL forKey:@"foo"]); 2878 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 2879 XCTAssertFalse([dict getEnum:NULL forKey:@"baz"]); 2880 XCTAssertFalse([dict getEnum:NULL forKey:@"mumble"]); 2881 [dict release]; 2882} 2883 2884- (void)testInplaceMutation { 2885 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 2886 const int32_t kValues[] = { 700, 701, 702, 703 }; 2887 GPBStringEnumDictionary *dict = 2888 [[GPBStringEnumDictionary alloc] initWithEnums:kValues 2889 forKeys:kKeys 2890 count:GPBARRAYSIZE(kValues)]; 2891 XCTAssertNotNil(dict); 2892 XCTAssertEqual(dict.count, 4U); 2893 int32_t value; 2894 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2895 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2896 XCTAssertEqual(value, 700); 2897 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 2898 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 2899 XCTAssertEqual(value, 701); 2900 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2901 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2902 XCTAssertEqual(value, 702); 2903 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 2904 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 2905 XCTAssertEqual(value, 703); 2906 2907 [dict setEnum:703 forKey:@"foo"]; 2908 XCTAssertEqual(dict.count, 4U); 2909 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2910 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2911 XCTAssertEqual(value, 703); 2912 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 2913 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 2914 XCTAssertEqual(value, 701); 2915 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2916 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2917 XCTAssertEqual(value, 702); 2918 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 2919 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 2920 XCTAssertEqual(value, 703); 2921 2922 [dict setEnum:701 forKey:@"mumble"]; 2923 XCTAssertEqual(dict.count, 4U); 2924 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2925 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2926 XCTAssertEqual(value, 703); 2927 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 2928 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 2929 XCTAssertEqual(value, 701); 2930 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2931 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2932 XCTAssertEqual(value, 702); 2933 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 2934 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 2935 XCTAssertEqual(value, 701); 2936 2937 const NSString *kKeys2[] = { @"bar", @"baz" }; 2938 const int32_t kValues2[] = { 702, 700 }; 2939 GPBStringEnumDictionary *dict2 = 2940 [[GPBStringEnumDictionary alloc] initWithEnums:kValues2 2941 forKeys:kKeys2 2942 count:GPBARRAYSIZE(kValues2)]; 2943 XCTAssertNotNil(dict2); 2944 [dict addRawEntriesFromDictionary:dict2]; 2945 XCTAssertEqual(dict.count, 4U); 2946 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 2947 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 2948 XCTAssertEqual(value, 703); 2949 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 2950 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 2951 XCTAssertEqual(value, 702); 2952 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 2953 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 2954 XCTAssertEqual(value, 700); 2955 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 2956 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 2957 XCTAssertEqual(value, 701); 2958 2959 [dict2 release]; 2960 [dict release]; 2961} 2962 2963@end 2964 2965#pragma mark - String -> Enum (Unknown Enums) 2966 2967@interface GPBStringEnumDictionaryUnknownEnumTests : XCTestCase 2968@end 2969 2970@implementation GPBStringEnumDictionaryUnknownEnumTests 2971 2972- (void)testRawBasics { 2973 const NSString *kKeys[] = { @"foo", @"bar", @"baz" }; 2974 const int32_t kValues[] = { 700, 801, 702 }; 2975 GPBStringEnumDictionary *dict = 2976 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 2977 rawValues:kValues 2978 forKeys:kKeys 2979 count:GPBARRAYSIZE(kValues)]; 2980 XCTAssertNotNil(dict); 2981 XCTAssertEqual(dict.count, 3U); 2982 XCTAssertTrue(dict.validationFunc == TestingEnum_IsValidValue); // Pointer comparison 2983 int32_t value; 2984 XCTAssertTrue([dict getRawValue:NULL forKey:@"foo"]); 2985 XCTAssertTrue([dict getRawValue:&value forKey:@"foo"]); 2986 XCTAssertEqual(value, 700); 2987 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 2988 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 2989 XCTAssertEqual(value, kGPBUnrecognizedEnumeratorValue); 2990 XCTAssertTrue([dict getRawValue:NULL forKey:@"bar"]); 2991 XCTAssertTrue([dict getRawValue:&value forKey:@"bar"]); 2992 XCTAssertEqual(value, 801); 2993 XCTAssertTrue([dict getRawValue:NULL forKey:@"baz"]); 2994 XCTAssertTrue([dict getRawValue:&value forKey:@"baz"]); 2995 XCTAssertEqual(value, 702); 2996 XCTAssertFalse([dict getRawValue:NULL forKey:@"mumble"]); 2997 2998 __block NSUInteger idx = 0; 2999 NSString **seenKeys = malloc(3 * sizeof(NSString*)); 3000 int32_t *seenValues = malloc(3 * sizeof(int32_t)); 3001 [dict enumerateKeysAndEnumsUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 3002 XCTAssertLessThan(idx, 3U); 3003 seenKeys[idx] = aKey; 3004 seenValues[idx] = aValue; 3005 XCTAssertNotEqual(stop, NULL); 3006 ++idx; 3007 }]; 3008 for (int i = 0; i < 3; ++i) { 3009 BOOL foundKey = NO; 3010 for (int j = 0; (j < 3) && !foundKey; ++j) { 3011 if ([kKeys[i] isEqual:seenKeys[j]]) { 3012 foundKey = YES; 3013 if (i == 1) { 3014 XCTAssertEqual(kGPBUnrecognizedEnumeratorValue, seenValues[j], @"i = %d, j = %d", i, j); 3015 } else { 3016 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 3017 } 3018 } 3019 } 3020 XCTAssertTrue(foundKey, @"i = %d", i); 3021 } 3022 idx = 0; 3023 [dict enumerateKeysAndRawValuesUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 3024 XCTAssertLessThan(idx, 3U); 3025 seenKeys[idx] = aKey; 3026 seenValues[idx] = aValue; 3027 XCTAssertNotEqual(stop, NULL); 3028 ++idx; 3029 }]; 3030 for (int i = 0; i < 3; ++i) { 3031 BOOL foundKey = NO; 3032 for (int j = 0; (j < 3) && !foundKey; ++j) { 3033 if ([kKeys[i] isEqual:seenKeys[j]]) { 3034 foundKey = YES; 3035 XCTAssertEqual(kValues[i], seenValues[j], @"i = %d, j = %d", i, j); 3036 } 3037 } 3038 XCTAssertTrue(foundKey, @"i = %d", i); 3039 } 3040 free(seenKeys); 3041 free(seenValues); 3042 3043 // Stopping the enumeration. 3044 idx = 0; 3045 [dict enumerateKeysAndRawValuesUsingBlock:^(NSString *aKey, int32_t aValue, BOOL *stop) { 3046 #pragma unused(aKey, aValue) 3047 if (idx == 1) *stop = YES; 3048 XCTAssertNotEqual(idx, 2U); 3049 ++idx; 3050 }]; 3051 [dict release]; 3052} 3053 3054- (void)testEqualityWithUnknowns { 3055 const NSString *kKeys1[] = { @"foo", @"bar", @"baz", @"mumble" }; 3056 const NSString *kKeys2[] = { @"bar", @"foo", @"mumble" }; 3057 const int32_t kValues1[] = { 700, 801, 702 }; // Unknown 3058 const int32_t kValues2[] = { 700, 803, 702 }; // Unknown 3059 const int32_t kValues3[] = { 700, 801, 702, 803 }; // Unknowns 3060 GPBStringEnumDictionary *dict1 = 3061 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3062 rawValues:kValues1 3063 forKeys:kKeys1 3064 count:GPBARRAYSIZE(kValues1)]; 3065 XCTAssertNotNil(dict1); 3066 GPBStringEnumDictionary *dict1prime = 3067 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3068 rawValues:kValues1 3069 forKeys:kKeys1 3070 count:GPBARRAYSIZE(kValues1)]; 3071 XCTAssertNotNil(dict1prime); 3072 GPBStringEnumDictionary *dict2 = 3073 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3074 rawValues:kValues2 3075 forKeys:kKeys1 3076 count:GPBARRAYSIZE(kValues2)]; 3077 XCTAssertNotNil(dict2); 3078 GPBStringEnumDictionary *dict3 = 3079 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3080 rawValues:kValues1 3081 forKeys:kKeys2 3082 count:GPBARRAYSIZE(kValues1)]; 3083 XCTAssertNotNil(dict3); 3084 GPBStringEnumDictionary *dict4 = 3085 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3086 rawValues:kValues3 3087 forKeys:kKeys1 3088 count:GPBARRAYSIZE(kValues3)]; 3089 XCTAssertNotNil(dict4); 3090 3091 // 1/1Prime should be different objects, but equal. 3092 XCTAssertNotEqual(dict1, dict1prime); 3093 XCTAssertEqualObjects(dict1, dict1prime); 3094 // Equal, so they must have same hash. 3095 XCTAssertEqual([dict1 hash], [dict1prime hash]); 3096 3097 // 2 is same keys, different values; not equal. 3098 XCTAssertNotEqualObjects(dict1, dict2); 3099 3100 // 3 is different keys, same values; not equal. 3101 XCTAssertNotEqualObjects(dict1, dict3); 3102 3103 // 4 extra pair; not equal 3104 XCTAssertNotEqualObjects(dict1, dict4); 3105 3106 [dict1 release]; 3107 [dict1prime release]; 3108 [dict2 release]; 3109 [dict3 release]; 3110 [dict4 release]; 3111} 3112 3113- (void)testCopyWithUnknowns { 3114 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 3115 const int32_t kValues[] = { 700, 801, 702, 803 }; // Unknown 3116 GPBStringEnumDictionary *dict = 3117 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3118 rawValues:kValues 3119 forKeys:kKeys 3120 count:GPBARRAYSIZE(kValues)]; 3121 XCTAssertNotNil(dict); 3122 3123 GPBStringEnumDictionary *dict2 = [dict copy]; 3124 XCTAssertNotNil(dict2); 3125 3126 // Should be new pointer, but equal objects. 3127 XCTAssertNotEqual(dict, dict2); 3128 XCTAssertEqual(dict.validationFunc, dict2.validationFunc); // Pointer comparison 3129 XCTAssertEqualObjects(dict, dict2); 3130 3131 [dict2 release]; 3132 [dict release]; 3133} 3134 3135- (void)testDictionaryFromDictionary { 3136 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 3137 const int32_t kValues[] = { 700, 801, 702, 803 }; // Unknowns 3138 GPBStringEnumDictionary *dict = 3139 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3140 rawValues:kValues 3141 forKeys:kKeys 3142 count:GPBARRAYSIZE(kValues)]; 3143 XCTAssertNotNil(dict); 3144 3145 GPBStringEnumDictionary *dict2 = 3146 [[GPBStringEnumDictionary alloc] initWithDictionary:dict]; 3147 XCTAssertNotNil(dict2); 3148 3149 // Should be new pointer, but equal objects. 3150 XCTAssertNotEqual(dict, dict2); 3151 XCTAssertEqualObjects(dict, dict2); 3152 XCTAssertEqual(dict.validationFunc, dict2.validationFunc); // Pointer comparison 3153 [dict2 release]; 3154 [dict release]; 3155} 3156 3157- (void)testUnknownAdds { 3158 GPBStringEnumDictionary *dict = 3159 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue]; 3160 XCTAssertNotNil(dict); 3161 3162 XCTAssertEqual(dict.count, 0U); 3163 XCTAssertThrowsSpecificNamed([dict setEnum:801 forKey:@"bar"], // Unknown 3164 NSException, NSInvalidArgumentException); 3165 XCTAssertEqual(dict.count, 0U); 3166 [dict setRawValue:801 forKey:@"bar"]; // Unknown 3167 XCTAssertEqual(dict.count, 1U); 3168 3169 const NSString *kKeys[] = { @"foo", @"baz", @"mumble" }; 3170 const int32_t kValues[] = { 700, 702, 803 }; // Unknown 3171 GPBStringEnumDictionary *dict2 = 3172 [[GPBStringEnumDictionary alloc] initWithEnums:kValues 3173 forKeys:kKeys 3174 count:GPBARRAYSIZE(kValues)]; 3175 XCTAssertNotNil(dict2); 3176 [dict addRawEntriesFromDictionary:dict2]; 3177 XCTAssertEqual(dict.count, 4U); 3178 3179 int32_t value; 3180 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 3181 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 3182 XCTAssertEqual(value, 700); 3183 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 3184 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 3185 XCTAssertEqual(value, kGPBUnrecognizedEnumeratorValue); 3186 XCTAssertTrue([dict getRawValue:NULL forKey:@"bar"]); 3187 XCTAssertTrue([dict getRawValue:&value forKey:@"bar"]); 3188 XCTAssertEqual(value, 801); 3189 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3190 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3191 XCTAssertEqual(value, 702); 3192 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 3193 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 3194 XCTAssertEqual(value, kGPBUnrecognizedEnumeratorValue); 3195 XCTAssertTrue([dict getRawValue:NULL forKey:@"mumble"]); 3196 XCTAssertTrue([dict getRawValue:&value forKey:@"mumble"]); 3197 XCTAssertEqual(value, 803); 3198 [dict2 release]; 3199 [dict release]; 3200} 3201 3202- (void)testUnknownRemove { 3203 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 3204 const int32_t kValues[] = { 700, 801, 702, 803 }; // Unknowns 3205 GPBStringEnumDictionary *dict = 3206 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3207 rawValues:kValues 3208 forKeys:kKeys 3209 count:GPBARRAYSIZE(kValues)]; 3210 XCTAssertNotNil(dict); 3211 XCTAssertEqual(dict.count, 4U); 3212 3213 [dict removeEnumForKey:@"bar"]; 3214 XCTAssertEqual(dict.count, 3U); 3215 int32_t value; 3216 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 3217 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 3218 XCTAssertEqual(value, 700); 3219 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 3220 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3221 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3222 XCTAssertEqual(value, 702); 3223 XCTAssertTrue([dict getRawValue:NULL forKey:@"mumble"]); 3224 XCTAssertTrue([dict getRawValue:&value forKey:@"mumble"]); 3225 XCTAssertEqual(value, 803); 3226 3227 // Remove again does nothing. 3228 [dict removeEnumForKey:@"bar"]; 3229 XCTAssertEqual(dict.count, 3U); 3230 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 3231 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 3232 XCTAssertEqual(value, 700); 3233 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 3234 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3235 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3236 XCTAssertEqual(value, 702); 3237 XCTAssertTrue([dict getRawValue:NULL forKey:@"mumble"]); 3238 XCTAssertTrue([dict getRawValue:&value forKey:@"mumble"]); 3239 XCTAssertEqual(value, 803); 3240 3241 [dict removeEnumForKey:@"mumble"]; 3242 XCTAssertEqual(dict.count, 2U); 3243 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 3244 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 3245 XCTAssertEqual(value, 700); 3246 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 3247 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3248 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3249 XCTAssertEqual(value, 702); 3250 XCTAssertFalse([dict getEnum:NULL forKey:@"mumble"]); 3251 3252 [dict removeAll]; 3253 XCTAssertEqual(dict.count, 0U); 3254 XCTAssertFalse([dict getEnum:NULL forKey:@"foo"]); 3255 XCTAssertFalse([dict getEnum:NULL forKey:@"bar"]); 3256 XCTAssertFalse([dict getEnum:NULL forKey:@"baz"]); 3257 XCTAssertFalse([dict getEnum:NULL forKey:@"mumble"]); 3258 [dict release]; 3259} 3260 3261- (void)testInplaceMutationUnknowns { 3262 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 3263 const int32_t kValues[] = { 700, 801, 702, 803 }; // Unknowns 3264 GPBStringEnumDictionary *dict = 3265 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3266 rawValues:kValues 3267 forKeys:kKeys 3268 count:GPBARRAYSIZE(kValues)]; 3269 XCTAssertNotNil(dict); 3270 XCTAssertEqual(dict.count, 4U); 3271 int32_t value; 3272 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 3273 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 3274 XCTAssertEqual(value, 700); 3275 XCTAssertTrue([dict getRawValue:NULL forKey:@"bar"]); 3276 XCTAssertTrue([dict getRawValue:&value forKey:@"bar"]); 3277 XCTAssertEqual(value, 801); 3278 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3279 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3280 XCTAssertEqual(value, 702); 3281 XCTAssertTrue([dict getRawValue:NULL forKey:@"mumble"]); 3282 XCTAssertTrue([dict getRawValue:&value forKey:@"mumble"]); 3283 XCTAssertEqual(value, 803); 3284 3285 XCTAssertThrowsSpecificNamed([dict setEnum:803 forKey:@"foo"], // Unknown 3286 NSException, NSInvalidArgumentException); 3287 XCTAssertEqual(dict.count, 4U); 3288 XCTAssertTrue([dict getEnum:NULL forKey:@"foo"]); 3289 XCTAssertTrue([dict getEnum:&value forKey:@"foo"]); 3290 XCTAssertEqual(value, 700); 3291 XCTAssertTrue([dict getRawValue:NULL forKey:@"bar"]); 3292 XCTAssertTrue([dict getRawValue:&value forKey:@"bar"]); 3293 XCTAssertEqual(value, 801); 3294 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3295 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3296 XCTAssertEqual(value, 702); 3297 XCTAssertTrue([dict getRawValue:NULL forKey:@"mumble"]); 3298 XCTAssertTrue([dict getRawValue:&value forKey:@"mumble"]); 3299 XCTAssertEqual(value, 803); 3300 3301 [dict setRawValue:803 forKey:@"foo"]; // Unknown 3302 XCTAssertEqual(dict.count, 4U); 3303 XCTAssertTrue([dict getRawValue:NULL forKey:@"foo"]); 3304 XCTAssertTrue([dict getRawValue:&value forKey:@"foo"]); 3305 XCTAssertEqual(value, 803); 3306 XCTAssertTrue([dict getRawValue:NULL forKey:@"bar"]); 3307 XCTAssertTrue([dict getRawValue:&value forKey:@"bar"]); 3308 XCTAssertEqual(value, 801); 3309 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3310 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3311 XCTAssertEqual(value, 702); 3312 XCTAssertTrue([dict getRawValue:NULL forKey:@"mumble"]); 3313 XCTAssertTrue([dict getRawValue:&value forKey:@"mumble"]); 3314 XCTAssertEqual(value, 803); 3315 3316 [dict setRawValue:700 forKey:@"mumble"]; 3317 XCTAssertEqual(dict.count, 4U); 3318 XCTAssertTrue([dict getRawValue:NULL forKey:@"foo"]); 3319 XCTAssertTrue([dict getRawValue:&value forKey:@"foo"]); 3320 XCTAssertEqual(value, 803); 3321 XCTAssertTrue([dict getRawValue:NULL forKey:@"bar"]); 3322 XCTAssertTrue([dict getRawValue:&value forKey:@"bar"]); 3323 XCTAssertEqual(value, 801); 3324 XCTAssertTrue([dict getEnum:NULL forKey:@"baz"]); 3325 XCTAssertTrue([dict getEnum:&value forKey:@"baz"]); 3326 XCTAssertEqual(value, 702); 3327 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 3328 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 3329 XCTAssertEqual(value, 700); 3330 3331 const NSString *kKeys2[] = { @"bar", @"baz" }; 3332 const int32_t kValues2[] = { 702, 801 }; // Unknown 3333 GPBStringEnumDictionary *dict2 = 3334 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3335 rawValues:kValues2 3336 forKeys:kKeys2 3337 count:GPBARRAYSIZE(kValues2)]; 3338 XCTAssertNotNil(dict2); 3339 [dict addRawEntriesFromDictionary:dict2]; 3340 XCTAssertEqual(dict.count, 4U); 3341 XCTAssertTrue([dict getRawValue:NULL forKey:@"foo"]); 3342 XCTAssertTrue([dict getRawValue:&value forKey:@"foo"]); 3343 XCTAssertEqual(value, 803); 3344 XCTAssertTrue([dict getEnum:NULL forKey:@"bar"]); 3345 XCTAssertTrue([dict getEnum:&value forKey:@"bar"]); 3346 XCTAssertEqual(value, 702); 3347 XCTAssertTrue([dict getRawValue:NULL forKey:@"baz"]); 3348 XCTAssertTrue([dict getRawValue:&value forKey:@"baz"]); 3349 XCTAssertEqual(value, 801); 3350 XCTAssertTrue([dict getEnum:NULL forKey:@"mumble"]); 3351 XCTAssertTrue([dict getEnum:&value forKey:@"mumble"]); 3352 XCTAssertEqual(value, 700); 3353 3354 [dict2 release]; 3355 [dict release]; 3356} 3357 3358- (void)testCopyUnknowns { 3359 const NSString *kKeys[] = { @"foo", @"bar", @"baz", @"mumble" }; 3360 const int32_t kValues[] = { 700, 801, 702, 803 }; 3361 GPBStringEnumDictionary *dict = 3362 [[GPBStringEnumDictionary alloc] initWithValidationFunction:TestingEnum_IsValidValue 3363 rawValues:kValues 3364 forKeys:kKeys 3365 count:GPBARRAYSIZE(kValues)]; 3366 XCTAssertNotNil(dict); 3367 3368 GPBStringEnumDictionary *dict2 = [dict copy]; 3369 XCTAssertNotNil(dict2); 3370 3371 // Should be new pointer, but equal objects. 3372 XCTAssertNotEqual(dict, dict2); 3373 XCTAssertEqualObjects(dict, dict2); 3374 XCTAssertEqual(dict.validationFunc, dict2.validationFunc); // Pointer comparison 3375 XCTAssertTrue([dict2 isKindOfClass:[GPBStringEnumDictionary class]]); 3376 3377 [dict2 release]; 3378 [dict release]; 3379} 3380 3381@end 3382 3383//%PDDM-EXPAND-END TESTS_FOR_POD_VALUES(String, NSString, *, Objects, @"foo", @"bar", @"baz", @"mumble") 3384 3385