Benchmark.m 31 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019
  1. //
  2. // Benchmark.m
  3. // CacheBenchmark
  4. //
  5. // Created by ibireme on 15/10/20.
  6. // Copyright (C) 2015 ibireme. All rights reserved.
  7. //
  8. #import "Benchmark.h"
  9. #import "YYCache.h"
  10. #import "PINCache.h"
  11. #import "TMCache.h"
  12. #import "YYThreadSafeDictionary.h"
  13. #import <QuartzCore/QuartzCore.h>
  14. @implementation Benchmark
  15. + (void)benchmark {
  16. @autoreleasepool {
  17. [self memoryCacheBenchmark];
  18. }
  19. // You should benchmark data writing first.
  20. // Before benchmark data reading, you should kill the app to avoid disk-in-memory cache.
  21. #define WRITE 1
  22. #define READ 1
  23. #define RANDOMLY 1
  24. #if WRITE
  25. printf("\n\n\nwrite\n");
  26. [self diskCacheClearSmallData];
  27. [self diskCacheClearLargeData];
  28. @autoreleasepool {
  29. [self diskCacheWriteSmallDataBenchmark];
  30. }
  31. @autoreleasepool {
  32. [self diskCacheWriteLargeDataBenchmark];
  33. }
  34. printf("\n\n\nreplace\n");
  35. @autoreleasepool {
  36. [self diskCacheWriteSmallDataBenchmark];
  37. }
  38. @autoreleasepool {
  39. [self diskCacheWriteLargeDataBenchmark];
  40. }
  41. #endif
  42. #if READ
  43. printf("\n\n\nread\n");
  44. @autoreleasepool {
  45. [self diskCacheReadSmallDataBenchmark:RANDOMLY];
  46. }
  47. @autoreleasepool {
  48. [self diskCacheReadLargeDataBenchmark:RANDOMLY];
  49. }
  50. printf("\n\n\nread again (with file-in-memory cache)\n");
  51. @autoreleasepool {
  52. [self diskCacheReadSmallDataBenchmark:RANDOMLY];
  53. }
  54. @autoreleasepool {
  55. [self diskCacheReadLargeDataBenchmark:RANDOMLY];
  56. }
  57. printf("\n\n\nread none exist\n");
  58. @autoreleasepool {
  59. [self diskCacheReadSmallDataNoneExist];
  60. }
  61. @autoreleasepool {
  62. [self diskCacheReadLargeDataNoneExist];
  63. }
  64. #endif
  65. printf("\n\n--fin--\n\n");
  66. }
  67. + (void)memoryCacheBenchmark {
  68. // 1.27 1.09
  69. // 2.86 5.57
  70. NSMutableDictionary *nsDict = [NSMutableDictionary new];
  71. YYThreadSafeDictionary *nsDictLock = [YYThreadSafeDictionary new];
  72. NSCache *ns = [NSCache new];
  73. PINMemoryCache *pin = [PINMemoryCache new];
  74. TMMemoryCache *tm = [TMMemoryCache new];
  75. YYMemoryCache *yy = [YYMemoryCache new];
  76. yy.releaseOnMainThread = YES;
  77. NSMutableArray *keys = [NSMutableArray new];
  78. NSMutableArray *values = [NSMutableArray new];
  79. int count = 200000;
  80. for (int i = 0; i < count; i++) {
  81. NSObject *key;
  82. key = @(i); // avoid string compare
  83. //key = @(i).description; // it will slow down NSCache...
  84. //key = [NSUUID UUID].UUIDString;
  85. NSData *value = [NSData dataWithBytes:&i length:sizeof(int)];
  86. [keys addObject:key];
  87. [values addObject:value];
  88. }
  89. NSTimeInterval begin, end, time;
  90. printf("\n===========================\n");
  91. printf("Memory cache set 200000 key-value pairs\n");
  92. begin = CACurrentMediaTime();
  93. @autoreleasepool {
  94. for (int i = 0; i < count; i++) {
  95. [nsDict setObject:values[i] forKey:keys[i]];
  96. }
  97. }
  98. end = CACurrentMediaTime();
  99. time = end - begin;
  100. printf("NSDictionary: %8.2f\n", time * 1000);
  101. begin = CACurrentMediaTime();
  102. @autoreleasepool {
  103. for (int i = 0; i < count; i++) {
  104. [nsDictLock setObject:values[i] forKey:keys[i]];
  105. }
  106. }
  107. end = CACurrentMediaTime();
  108. time = end - begin;
  109. printf("NSDict+Lock: %8.2f\n", time * 1000);
  110. begin = CACurrentMediaTime();
  111. @autoreleasepool {
  112. for (int i = 0; i < count; i++) {
  113. [yy setObject:values[i] forKey:keys[i]];
  114. }
  115. }
  116. end = CACurrentMediaTime();
  117. time = end - begin;
  118. printf("YYMemoryCache: %8.2f\n", time * 1000);
  119. begin = CACurrentMediaTime();
  120. @autoreleasepool {
  121. for (int i = 0; i < count; i++) {
  122. [pin setObject:values[i] forKey:keys[i]];
  123. }
  124. }
  125. end = CACurrentMediaTime();
  126. time = end - begin;
  127. printf("PINMemoryCache: %8.2f\n", time * 1000);
  128. begin = CACurrentMediaTime();
  129. @autoreleasepool {
  130. for (int i = 0; i < count; i++) {
  131. [ns setObject:values[i] forKey:keys[i]];
  132. }
  133. }
  134. end = CACurrentMediaTime();
  135. time = end - begin;
  136. printf("NSCache: %8.2f\n", time * 1000);
  137. begin = CACurrentMediaTime();
  138. @autoreleasepool {
  139. for (int i = 0; i < count / 100; i++) {
  140. [tm setObject:values[i] forKey:keys[i]]; // too slow...
  141. }
  142. }
  143. end = CACurrentMediaTime();
  144. time = end - begin;
  145. printf("TMMemoryCache: %8.2f\n", time * 1000 * 100);
  146. printf("\n===========================\n");
  147. printf("Memory cache set 200000 key-value pairs without resize\n");
  148. [nsDict removeAllObjects];
  149. begin = CACurrentMediaTime();
  150. @autoreleasepool {
  151. for (int i = 0; i < count; i++) {
  152. [nsDict setObject:values[i] forKey:keys[i]];
  153. }
  154. }
  155. end = CACurrentMediaTime();
  156. time = end - begin;
  157. printf("NSDictionary: %8.2f\n", time * 1000);
  158. [nsDictLock removeAllObjects];
  159. begin = CACurrentMediaTime();
  160. @autoreleasepool {
  161. for (int i = 0; i < count; i++) {
  162. [nsDictLock setObject:values[i] forKey:keys[i]];
  163. }
  164. }
  165. end = CACurrentMediaTime();
  166. time = end - begin;
  167. printf("NSDict+Lock: %8.2f\n", time * 1000);
  168. //[yy removeAllObjects]; // it will rebuild inner cache...
  169. for (id key in keys) [yy removeObjectForKey:key]; // slow than 'removeAllObjects'
  170. begin = CACurrentMediaTime();
  171. @autoreleasepool {
  172. for (int i = 0; i < count; i++) {
  173. [yy setObject:values[i] forKey:keys[i]];
  174. }
  175. }
  176. end = CACurrentMediaTime();
  177. time = end - begin;
  178. printf("YYMemoryCache: %8.2f\n", time * 1000);
  179. [pin removeAllObjects];
  180. begin = CACurrentMediaTime();
  181. @autoreleasepool {
  182. for (int i = 0; i < count; i++) {
  183. [pin setObject:values[i] forKey:keys[i]];
  184. }
  185. }
  186. end = CACurrentMediaTime();
  187. time = end - begin;
  188. printf("PINMemoryCache: %8.2f\n", time * 1000);
  189. [ns removeAllObjects];
  190. begin = CACurrentMediaTime();
  191. @autoreleasepool {
  192. for (int i = 0; i < count; i++) {
  193. [ns setObject:values[i] forKey:keys[i]];
  194. }
  195. }
  196. end = CACurrentMediaTime();
  197. time = end - begin;
  198. printf("NSCache: %8.2f\n", time * 1000);
  199. [tm removeAllObjects];
  200. begin = CACurrentMediaTime();
  201. @autoreleasepool {
  202. for (int i = 0; i < count / 100; i++) {
  203. [tm setObject:values[i] forKey:keys[i]]; // too slow...
  204. }
  205. }
  206. end = CACurrentMediaTime();
  207. time = end - begin;
  208. printf("TMMemoryCache: %8.2f\n", time * 1000 * 100);
  209. printf("\n===========================\n");
  210. printf("Memory cache get 200000 key-value pairs\n");
  211. begin = CACurrentMediaTime();
  212. @autoreleasepool {
  213. for (int i = 0; i < count; i++) {
  214. [nsDict objectForKey:keys[i]];
  215. }
  216. }
  217. end = CACurrentMediaTime();
  218. time = end - begin;
  219. printf("NSDictionary: %8.2f\n", time * 1000);
  220. begin = CACurrentMediaTime();
  221. @autoreleasepool {
  222. for (int i = 0; i < count; i++) {
  223. [nsDictLock objectForKey:keys[i]];
  224. }
  225. }
  226. end = CACurrentMediaTime();
  227. time = end - begin;
  228. printf("NSDict+Lock: %8.2f\n", time * 1000);
  229. begin = CACurrentMediaTime();
  230. @autoreleasepool {
  231. for (int i = 0; i < count; i++) {
  232. [yy objectForKey:keys[i]];
  233. }
  234. }
  235. end = CACurrentMediaTime();
  236. time = end - begin;
  237. printf("YYMemoryCache: %8.2f\n", time * 1000);
  238. begin = CACurrentMediaTime();
  239. @autoreleasepool {
  240. for (int i = 0; i < count; i++) {
  241. [pin objectForKey:keys[i]];
  242. }
  243. }
  244. end = CACurrentMediaTime();
  245. time = end - begin;
  246. printf("PINMemoryCache: %8.2f\n", time * 1000);
  247. begin = CACurrentMediaTime();
  248. @autoreleasepool {
  249. for (int i = 0; i < count; i++) {
  250. [ns objectForKey:keys[i]];
  251. }
  252. }
  253. end = CACurrentMediaTime();
  254. time = end - begin;
  255. printf("NSCache: %8.2f\n", time * 1000);
  256. begin = CACurrentMediaTime();
  257. @autoreleasepool {
  258. for (int i = 0; i < count / 100; i++) {
  259. [tm objectForKey:keys[i]];
  260. }
  261. }
  262. end = CACurrentMediaTime();
  263. time = end - begin;
  264. printf("TMMemoryCache: %8.2f\n", time * 1000 * 100);
  265. printf("\n===========================\n");
  266. printf("Memory cache get 100000 key-value pairs randomly\n");
  267. for (NSUInteger i = keys.count; i > 1; i--) {
  268. [keys exchangeObjectAtIndex:(i - 1) withObjectAtIndex:arc4random_uniform((u_int32_t)i)];
  269. }
  270. begin = CACurrentMediaTime();
  271. @autoreleasepool {
  272. for (int i = 0; i < count; i++) {
  273. [nsDict objectForKey:keys[i]];
  274. }
  275. }
  276. end = CACurrentMediaTime();
  277. time = end - begin;
  278. printf("NSDictionary: %8.2f\n", time * 1000);
  279. begin = CACurrentMediaTime();
  280. @autoreleasepool {
  281. for (int i = 0; i < count; i++) {
  282. [nsDictLock objectForKey:keys[i]];
  283. }
  284. }
  285. end = CACurrentMediaTime();
  286. time = end - begin;
  287. printf("NSDict+Lock: %8.2f\n", time * 1000);
  288. begin = CACurrentMediaTime();
  289. @autoreleasepool {
  290. for (int i = 0; i < count; i++) {
  291. [yy objectForKey:keys[i]];
  292. }
  293. }
  294. end = CACurrentMediaTime();
  295. time = end - begin;
  296. printf("YYMemoryCache: %8.2f\n", time * 1000);
  297. begin = CACurrentMediaTime();
  298. @autoreleasepool {
  299. for (int i = 0; i < count; i++) {
  300. [pin objectForKey:keys[i]];
  301. }
  302. }
  303. end = CACurrentMediaTime();
  304. time = end - begin;
  305. printf("PINMemoryCache: %8.2f\n", time * 1000);
  306. begin = CACurrentMediaTime();
  307. @autoreleasepool {
  308. for (int i = 0; i < count; i++) {
  309. [ns objectForKey:keys[i]];
  310. }
  311. }
  312. end = CACurrentMediaTime();
  313. time = end - begin;
  314. printf("NSCache: %8.2f\n", time * 1000);
  315. begin = CACurrentMediaTime();
  316. @autoreleasepool {
  317. for (int i = 0; i < count / 100; i++) {
  318. [tm objectForKey:keys[i]];
  319. }
  320. }
  321. end = CACurrentMediaTime();
  322. time = end - begin;
  323. printf("TMMemoryCache: %8.2f\n", time * 1000 * 100);
  324. printf("\n===========================\n");
  325. printf("Memory cache get 200000 key-value pairs none exist\n");
  326. for (int i = 0; i < count; i++) {
  327. NSObject *key;
  328. key = @(i + count); // avoid string compare
  329. [keys addObject:key];
  330. }
  331. for (NSUInteger i = keys.count; i > 1; i--) {
  332. [keys exchangeObjectAtIndex:(i - 1) withObjectAtIndex:arc4random_uniform((u_int32_t)i)];
  333. }
  334. begin = CACurrentMediaTime();
  335. @autoreleasepool {
  336. for (int i = 0; i < count; i++) {
  337. [nsDict objectForKey:keys[i]];
  338. }
  339. }
  340. end = CACurrentMediaTime();
  341. time = end - begin;
  342. printf("NSDictionary: %8.2f\n", time * 1000);
  343. begin = CACurrentMediaTime();
  344. @autoreleasepool {
  345. for (int i = 0; i < count; i++) {
  346. [nsDictLock objectForKey:keys[i]];
  347. }
  348. }
  349. end = CACurrentMediaTime();
  350. time = end - begin;
  351. printf("NSDict+Lock: %8.2f\n", time * 1000);
  352. begin = CACurrentMediaTime();
  353. @autoreleasepool {
  354. for (int i = 0; i < count; i++) {
  355. [yy objectForKey:keys[i]];
  356. }
  357. }
  358. end = CACurrentMediaTime();
  359. time = end - begin;
  360. printf("YYMemoryCache: %8.2f\n", time * 1000);
  361. begin = CACurrentMediaTime();
  362. @autoreleasepool {
  363. for (int i = 0; i < count; i++) {
  364. [pin objectForKey:keys[i]];
  365. }
  366. }
  367. end = CACurrentMediaTime();
  368. time = end - begin;
  369. printf("PINMemoryCache: %8.2f\n", time * 1000);
  370. begin = CACurrentMediaTime();
  371. @autoreleasepool {
  372. for (int i = 0; i < count; i++) {
  373. [ns objectForKey:keys[i]];
  374. }
  375. }
  376. end = CACurrentMediaTime();
  377. time = end - begin;
  378. printf("NSCache: %8.2f\n", time * 1000);
  379. begin = CACurrentMediaTime();
  380. @autoreleasepool {
  381. for (int i = 0; i < count / 100; i++) {
  382. [tm objectForKey:keys[i]];
  383. }
  384. }
  385. end = CACurrentMediaTime();
  386. time = end - begin;
  387. printf("TMMemoryCache: %8.2f\n", time * 1000 * 100);
  388. }
  389. + (void)diskCacheClearSmallData {
  390. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  391. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkSmall"];
  392. [[NSFileManager defaultManager] removeItemAtPath:basePath error:nil];
  393. }
  394. + (void)diskCacheClearLargeData {
  395. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  396. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkLarge"];
  397. [[NSFileManager defaultManager] removeItemAtPath:basePath error:nil];
  398. }
  399. + (void)diskCacheWriteSmallDataBenchmark {
  400. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  401. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkSmall"];
  402. YYKVStorage *yykvFile = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvFile"] type:YYKVStorageTypeFile];
  403. YYKVStorage *yykvSQLite = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvSQLite"] type:YYKVStorageTypeSQLite];
  404. YYDiskCache *yy = [[YYDiskCache alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yy"]];
  405. PINDiskCache *pin = [[PINDiskCache alloc] initWithName:@"pin" rootPath:[basePath stringByAppendingPathComponent:@"pin"]];
  406. TMDiskCache *tm = [[TMDiskCache alloc] initWithName:@"tm" rootPath:[basePath stringByAppendingPathComponent:@"tm"]];
  407. int count = 1000;
  408. NSMutableArray *keys = [NSMutableArray new];
  409. NSMutableArray *values = [NSMutableArray new];
  410. for (int i = 0; i < count; i++) {
  411. NSString *key = @(i).description;
  412. NSNumber *value = @(i);
  413. [keys addObject:key];
  414. [values addObject:value];
  415. }
  416. NSTimeInterval begin, end, time;
  417. printf("\n===========================\n");
  418. printf("Disk cache set 1000 key-value pairs (value is NSNumber)\n");
  419. begin = CACurrentMediaTime();
  420. @autoreleasepool {
  421. for (int i = 0; i < count; i++) {
  422. [yykvFile saveItemWithKey:keys[i] value:[NSKeyedArchiver archivedDataWithRootObject:values[i]] filename:keys[i] extendedData:nil];
  423. }
  424. }
  425. end = CACurrentMediaTime();
  426. time = end - begin;
  427. printf("YYKVFile: %8.2f\n", time * 1000);
  428. begin = CACurrentMediaTime();
  429. @autoreleasepool {
  430. for (int i = 0; i < count; i++) {
  431. [yykvSQLite saveItemWithKey:keys[i] value:[NSKeyedArchiver archivedDataWithRootObject:values[i]]];
  432. }
  433. }
  434. end = CACurrentMediaTime();
  435. time = end - begin;
  436. printf("YYKVSQLite: %8.2f\n", time * 1000);
  437. begin = CACurrentMediaTime();
  438. @autoreleasepool {
  439. for (int i = 0; i < count; i++) {
  440. [yy setObject:values[i] forKey:keys[i]];
  441. }
  442. }
  443. end = CACurrentMediaTime();
  444. time = end - begin;
  445. printf("YYDiskCache: %8.2f\n", time * 1000);
  446. begin = CACurrentMediaTime();
  447. @autoreleasepool {
  448. for (int i = 0; i < count; i++) {
  449. [pin setObject:values[i] forKey:keys[i]];
  450. }
  451. }
  452. end = CACurrentMediaTime();
  453. time = end - begin;
  454. printf("PINDiskCache: %8.2f\n", time * 1000);
  455. begin = CACurrentMediaTime();
  456. @autoreleasepool {
  457. for (int i = 0; i < count; i++) {
  458. [tm setObject:values[i] forKey:keys[i]];
  459. }
  460. }
  461. end = CACurrentMediaTime();
  462. time = end - begin;
  463. printf("TMDiskCache: %8.2f\n", time * 1000);
  464. }
  465. + (void)diskCacheWriteLargeDataBenchmark {
  466. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  467. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkLarge"];
  468. YYKVStorage *yykvFile = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvFile"] type:YYKVStorageTypeFile];
  469. YYKVStorage *yykvSQLite = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvSQLite"] type:YYKVStorageTypeSQLite];
  470. YYDiskCache *yy = [[YYDiskCache alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yy"]];
  471. yy.customArchiveBlock = ^(id object) {return object;};
  472. yy.customUnarchiveBlock = ^(NSData *object) {return object;};
  473. PINDiskCache *pin = [[PINDiskCache alloc] initWithName:@"pin" rootPath:[basePath stringByAppendingPathComponent:@"pin"]];
  474. TMDiskCache *tm = [[TMDiskCache alloc] initWithName:@"tm" rootPath:[basePath stringByAppendingPathComponent:@"tm"]];
  475. int count = 1000;
  476. NSMutableArray *keys = [NSMutableArray new];
  477. for (int i = 0; i < count; i++) {
  478. NSString *key = @(i).description;
  479. [keys addObject:key];
  480. }
  481. NSMutableData *dataValue = [NSMutableData new]; // 32KB
  482. for (int i = 0; i < 100 * 1024; i++) {
  483. [dataValue appendBytes:&i length:1];
  484. }
  485. NSTimeInterval begin, end, time;
  486. printf("\n===========================\n");
  487. printf("Disk cache set 1000 key-value pairs (value is NSData(100KB))\n");
  488. begin = CACurrentMediaTime();
  489. @autoreleasepool {
  490. for (int i = 0; i < count; i++) {
  491. [yykvFile saveItemWithKey:keys[i] value:dataValue filename:keys[i] extendedData:nil];
  492. }
  493. }
  494. end = CACurrentMediaTime();
  495. time = end - begin;
  496. printf("YYKVFile: %8.2f\n", time * 1000);
  497. begin = CACurrentMediaTime();
  498. @autoreleasepool {
  499. for (int i = 0; i < count; i++) {
  500. [yykvSQLite saveItemWithKey:keys[i] value:dataValue];
  501. }
  502. }
  503. end = CACurrentMediaTime();
  504. time = end - begin;
  505. printf("YYKVSQLite: %8.2f\n", time * 1000);
  506. begin = CACurrentMediaTime();
  507. @autoreleasepool {
  508. for (int i = 0; i < count; i++) {
  509. [yy setObject:dataValue forKey:keys[i]];
  510. }
  511. }
  512. end = CACurrentMediaTime();
  513. time = end - begin;
  514. printf("YYDiskCache: %8.2f\n", time * 1000);
  515. begin = CACurrentMediaTime();
  516. @autoreleasepool {
  517. for (int i = 0; i < count; i++) {
  518. [pin setObject:dataValue forKey:keys[i]];
  519. }
  520. }
  521. end = CACurrentMediaTime();
  522. time = end - begin;
  523. printf("PINDiskCache: %8.2f\n", time * 1000);
  524. begin = CACurrentMediaTime();
  525. @autoreleasepool {
  526. for (int i = 0; i < count; i++) {
  527. [tm setObject:dataValue forKey:keys[i]];
  528. }
  529. }
  530. end = CACurrentMediaTime();
  531. time = end - begin;
  532. printf("TMDiskCache: %8.2f\n", time * 1000);
  533. }
  534. + (void)diskCacheReadSmallDataBenchmark:(BOOL)randomly {
  535. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  536. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkSmall"];
  537. YYKVStorage *yykvFile = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvFile"] type:YYKVStorageTypeFile];
  538. YYKVStorage *yykvSQLite = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvSQLite"] type:YYKVStorageTypeSQLite];
  539. YYDiskCache *yy = [[YYDiskCache alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yy"]];
  540. PINDiskCache *pin = [[PINDiskCache alloc] initWithName:@"pin" rootPath:[basePath stringByAppendingPathComponent:@"pin"]];
  541. TMDiskCache *tm = [[TMDiskCache alloc] initWithName:@"tm" rootPath:[basePath stringByAppendingPathComponent:@"tm"]];
  542. int count = 1000;
  543. NSMutableArray *keys = [NSMutableArray new];
  544. for (int i = 0; i < count; i++) {
  545. NSString *key = @(i).description;
  546. [keys addObject:key];
  547. }
  548. if (randomly) {
  549. for (NSUInteger i = keys.count; i > 1; i--) {
  550. [keys exchangeObjectAtIndex:(i - 1) withObjectAtIndex:arc4random_uniform((u_int32_t)i)];
  551. }
  552. }
  553. NSTimeInterval begin, end, time;
  554. printf("\n===========================\n");
  555. printf("Disk cache get 1000 key-value pairs %s(value is NSNumber)\n", (randomly ? "randomly " : ""));
  556. begin = CACurrentMediaTime();
  557. @autoreleasepool {
  558. for (int i = 0; i < count; i++) {
  559. YYKVStorageItem *item = [yykvFile getItemForKey:keys[i]];
  560. NSNumber *value = [NSKeyedUnarchiver unarchiveObjectWithData:item.value];
  561. if (!value) printf("error!");
  562. }
  563. }
  564. end = CACurrentMediaTime();
  565. time = end - begin;
  566. printf("YYKVFile: %8.2f\n", time * 1000);
  567. begin = CACurrentMediaTime();
  568. @autoreleasepool {
  569. for (int i = 0; i < count; i++) {
  570. YYKVStorageItem *item = [yykvSQLite getItemForKey:keys[i]];
  571. NSNumber *value = [NSKeyedUnarchiver unarchiveObjectWithData:item.value];
  572. if (!value) printf("error!");
  573. }
  574. }
  575. end = CACurrentMediaTime();
  576. time = end - begin;
  577. printf("YYKVSQLite: %8.2f\n", time * 1000);
  578. begin = CACurrentMediaTime();
  579. @autoreleasepool {
  580. for (int i = 0; i < count; i++) {
  581. NSNumber *value = (id)[yy objectForKey:keys[i]];
  582. if (!value) printf("error!");
  583. }
  584. }
  585. end = CACurrentMediaTime();
  586. time = end - begin;
  587. printf("YYDiskCache: %8.2f\n", time * 1000);
  588. begin = CACurrentMediaTime();
  589. @autoreleasepool {
  590. for (int i = 0; i < count; i++) {
  591. NSNumber *value = (id)[pin objectForKey:keys[i]];
  592. if (!value) printf("error!");
  593. }
  594. }
  595. end = CACurrentMediaTime();
  596. time = end - begin;
  597. printf("PINDiskCache: %8.2f\n", time * 1000);
  598. begin = CACurrentMediaTime();
  599. @autoreleasepool {
  600. for (int i = 0; i < count; i++) {
  601. NSNumber *value = (id)[tm objectForKey:keys[i]];
  602. if (!value) printf("error!");
  603. }
  604. }
  605. end = CACurrentMediaTime();
  606. time = end - begin;
  607. printf("TMDiskCache: %8.2f\n", time * 1000);
  608. }
  609. + (void)diskCacheReadLargeDataBenchmark:(BOOL)randomly {
  610. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  611. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkLarge"];
  612. YYKVStorage *yykvFile = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvFile"] type:YYKVStorageTypeFile];
  613. YYKVStorage *yykvSQLite = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvSQLite"] type:YYKVStorageTypeSQLite];
  614. YYDiskCache *yy = [[YYDiskCache alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yy"]];
  615. yy.customArchiveBlock = ^(id object) {return object;};
  616. yy.customUnarchiveBlock = ^(NSData *object) {return object;};
  617. PINDiskCache *pin = [[PINDiskCache alloc] initWithName:@"pin" rootPath:[basePath stringByAppendingPathComponent:@"pin"]];
  618. TMDiskCache *tm = [[TMDiskCache alloc] initWithName:@"tm" rootPath:[basePath stringByAppendingPathComponent:@"tm"]];
  619. int count = 1000;
  620. NSMutableArray *keys = [NSMutableArray new];
  621. for (int i = 0; i < count; i++) {
  622. NSString *key = @(i).description;
  623. [keys addObject:key];
  624. }
  625. if (randomly) {
  626. for (NSUInteger i = keys.count; i > 1; i--) {
  627. [keys exchangeObjectAtIndex:(i - 1) withObjectAtIndex:arc4random_uniform((u_int32_t)i)];
  628. }
  629. }
  630. NSTimeInterval begin, end, time;
  631. printf("\n===========================\n");
  632. printf("Disk cache get 1000 key-value pairs %s(value is NSData(100KB))\n", (randomly ? "randomly " : ""));
  633. begin = CACurrentMediaTime();
  634. @autoreleasepool {
  635. for (int i = 0; i < count; i++) {
  636. YYKVStorageItem *item = [yykvFile getItemForKey:keys[i]];
  637. NSData *value = item.value;
  638. if (!value) printf("error!");
  639. }
  640. }
  641. end = CACurrentMediaTime();
  642. time = end - begin;
  643. printf("YYKVFile: %8.2f\n", time * 1000);
  644. begin = CACurrentMediaTime();
  645. @autoreleasepool {
  646. for (int i = 0; i < count; i++) {
  647. YYKVStorageItem *item = [yykvSQLite getItemForKey:keys[i]];
  648. NSData *value = item.value;
  649. if (!value) printf("error!");
  650. }
  651. }
  652. end = CACurrentMediaTime();
  653. time = end - begin;
  654. printf("YYKVSQLite: %8.2f\n", time * 1000);
  655. begin = CACurrentMediaTime();
  656. @autoreleasepool {
  657. for (int i = 0; i < count; i++) {
  658. NSData *value = (id)[yy objectForKey:keys[i]];
  659. if (!value) printf("error!");
  660. }
  661. }
  662. end = CACurrentMediaTime();
  663. time = end - begin;
  664. printf("YYDiskCache: %8.2f\n", time * 1000);
  665. begin = CACurrentMediaTime();
  666. @autoreleasepool {
  667. for (int i = 0; i < count; i++) {
  668. NSData *value = (id)[pin objectForKey:keys[i]];
  669. if (!value) printf("error!");
  670. }
  671. }
  672. end = CACurrentMediaTime();
  673. time = end - begin;
  674. printf("PINDiskCache: %8.2f\n", time * 1000);
  675. begin = CACurrentMediaTime();
  676. @autoreleasepool {
  677. for (int i = 0; i < count; i++) {
  678. NSData *value = (id)[tm objectForKey:keys[i]];
  679. if (!value) printf("error!");
  680. }
  681. }
  682. end = CACurrentMediaTime();
  683. time = end - begin;
  684. printf("TMDiskCache: %8.2f\n", time * 1000);
  685. }
  686. + (void)diskCacheReadSmallDataNoneExist {
  687. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  688. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkSmall"];
  689. YYKVStorage *yykvFile = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvFile"] type:YYKVStorageTypeFile];
  690. YYKVStorage *yykvSQLite = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvSQLite"] type:YYKVStorageTypeSQLite];
  691. YYDiskCache *yy = [[YYDiskCache alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yy"]];
  692. PINDiskCache *pin = [[PINDiskCache alloc] initWithName:@"pin" rootPath:[basePath stringByAppendingPathComponent:@"pin"]];
  693. TMDiskCache *tm = [[TMDiskCache alloc] initWithName:@"tm" rootPath:[basePath stringByAppendingPathComponent:@"tm"]];
  694. int count = 1000;
  695. NSMutableArray *keys = [NSMutableArray new];
  696. for (int i = 0; i < count; i++) {
  697. NSString *key = @(i + count).description;
  698. [keys addObject:key];
  699. }
  700. NSTimeInterval begin, end, time;
  701. printf("\n===========================\n");
  702. printf("Disk cache get 1000 key-value pairs none exist\n");
  703. begin = CACurrentMediaTime();
  704. @autoreleasepool {
  705. for (int i = 0; i < count; i++) {
  706. YYKVStorageItem *item = [yykvFile getItemForKey:keys[i]];
  707. if (item.value) printf("error!");
  708. }
  709. }
  710. end = CACurrentMediaTime();
  711. time = end - begin;
  712. printf("YYKVFile: %8.2f\n", time * 1000);
  713. begin = CACurrentMediaTime();
  714. @autoreleasepool {
  715. for (int i = 0; i < count; i++) {
  716. YYKVStorageItem *item = [yykvSQLite getItemForKey:keys[i]];
  717. if (item.value) printf("error!");
  718. }
  719. }
  720. end = CACurrentMediaTime();
  721. time = end - begin;
  722. printf("YYKVSQLite: %8.2f\n", time * 1000);
  723. begin = CACurrentMediaTime();
  724. @autoreleasepool {
  725. for (int i = 0; i < count; i++) {
  726. NSNumber *value = (id)[yy objectForKey:keys[i]];
  727. if (value) printf("error!");
  728. }
  729. }
  730. end = CACurrentMediaTime();
  731. time = end - begin;
  732. printf("YYDiskCache: %8.2f\n", time * 1000);
  733. begin = CACurrentMediaTime();
  734. @autoreleasepool {
  735. for (int i = 0; i < count; i++) {
  736. NSNumber *value = (id)[pin objectForKey:keys[i]];
  737. if (value) printf("error!");
  738. }
  739. }
  740. end = CACurrentMediaTime();
  741. time = end - begin;
  742. printf("PINDiskCache: %8.2f\n", time * 1000);
  743. begin = CACurrentMediaTime();
  744. @autoreleasepool {
  745. for (int i = 0; i < count; i++) {
  746. NSNumber *value = (id)[tm objectForKey:keys[i]];
  747. if (value) printf("error!");
  748. }
  749. }
  750. end = CACurrentMediaTime();
  751. time = end - begin;
  752. printf("TMDiskCache: %8.2f\n", time * 1000);
  753. }
  754. + (void)diskCacheReadLargeDataNoneExist {
  755. NSString *basePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) firstObject];
  756. basePath = [basePath stringByAppendingPathComponent:@"FileCacheBenchmarkLarge"];
  757. YYKVStorage *yykvFile = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvFile"] type:YYKVStorageTypeFile];
  758. YYKVStorage *yykvSQLite = [[YYKVStorage alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yykvSQLite"] type:YYKVStorageTypeSQLite];
  759. YYDiskCache *yy = [[YYDiskCache alloc] initWithPath:[basePath stringByAppendingPathComponent:@"yy"]];
  760. yy.customArchiveBlock = ^(id object) {return object;};
  761. yy.customUnarchiveBlock = ^(NSData *object) {return object;};
  762. PINDiskCache *pin = [[PINDiskCache alloc] initWithName:@"pin" rootPath:[basePath stringByAppendingPathComponent:@"pin"]];
  763. TMDiskCache *tm = [[TMDiskCache alloc] initWithName:@"tm" rootPath:[basePath stringByAppendingPathComponent:@"tm"]];
  764. int count = 1000;
  765. NSMutableArray *keys = [NSMutableArray new];
  766. for (int i = 0; i < count; i++) {
  767. NSString *key = @(i + count).description;
  768. [keys addObject:key];
  769. }
  770. NSTimeInterval begin, end, time;
  771. printf("\n===========================\n");
  772. printf("Disk cache get 1000 key-value pairs none exist\n");
  773. begin = CACurrentMediaTime();
  774. @autoreleasepool {
  775. for (int i = 0; i < count; i++) {
  776. YYKVStorageItem *item = [yykvFile getItemForKey:keys[i]];
  777. if (item.value) printf("error!");
  778. }
  779. }
  780. end = CACurrentMediaTime();
  781. time = end - begin;
  782. printf("YYKVFile: %8.2f\n", time * 1000);
  783. begin = CACurrentMediaTime();
  784. @autoreleasepool {
  785. for (int i = 0; i < count; i++) {
  786. YYKVStorageItem *item = [yykvSQLite getItemForKey:keys[i]];
  787. if (item.value) printf("error!");
  788. }
  789. }
  790. end = CACurrentMediaTime();
  791. time = end - begin;
  792. printf("YYKVSQLite: %8.2f\n", time * 1000);
  793. begin = CACurrentMediaTime();
  794. @autoreleasepool {
  795. for (int i = 0; i < count; i++) {
  796. NSData *value = (id)[yy objectForKey:keys[i]];
  797. if (value) printf("error!");
  798. }
  799. }
  800. end = CACurrentMediaTime();
  801. time = end - begin;
  802. printf("YYDiskCache: %8.2f\n", time * 1000);
  803. begin = CACurrentMediaTime();
  804. @autoreleasepool {
  805. for (int i = 0; i < count; i++) {
  806. NSData *value = (id)[pin objectForKey:keys[i]];
  807. if (value) printf("error!");
  808. }
  809. }
  810. end = CACurrentMediaTime();
  811. time = end - begin;
  812. printf("PINDiskCache: %8.2f\n", time * 1000);
  813. begin = CACurrentMediaTime();
  814. @autoreleasepool {
  815. for (int i = 0; i < count; i++) {
  816. NSData *value = (id)[tm objectForKey:keys[i]];
  817. if (value) printf("error!");
  818. }
  819. }
  820. end = CACurrentMediaTime();
  821. time = end - begin;
  822. printf("TMDiskCache: %8.2f\n", time * 1000);
  823. }
  824. @end