99#import " CDSemanticString.h"
1010
1111@interface CDSemanticStringStaple : NSObject
12+
1213@property (strong , nonatomic ) NSString *string;
1314@property (nonatomic ) CDSemanticType type;
15+
16+ @property (nonatomic ) CDSemanticStringStaple *next;
17+
1418@end
1519
1620@implementation CDSemanticStringStaple
1721@end
1822
1923
2024@implementation CDSemanticString {
21- NSMutableArray <CDSemanticStringStaple *> *_components;
25+ CDSemanticStringStaple *_head;
26+ CDSemanticStringStaple *_tail;
2227}
2328
2429- (instancetype )init {
2530 if (self = [super init ]) {
2631 _length = 0 ;
27- _components = [NSMutableArray array ];
2832 }
2933 return self;
3034}
3135
36+ - (void )dealloc {
37+ CDSemanticStringStaple *head = _head;
38+ _head = nil ; // i.e. release
39+ while (head != nil ) {
40+ /* `head` gets released because it's no longer referenced here */
41+ head = head.next ;
42+ }
43+ }
44+
3245- (void )appendSemanticString : (CDSemanticString *)semanticString {
33- [_components addObjectsFromArray: semanticString->_components];
46+ if (_tail) {
47+ _tail.next = semanticString->_head ;
48+ } else {
49+ _head = semanticString->_head ;
50+ }
51+ _tail = semanticString->_tail ;
3452 _length += semanticString.length ;
3553}
3654
@@ -39,33 +57,40 @@ - (void)appendString:(NSString *)string semanticType:(CDSemanticType)type {
3957 CDSemanticStringStaple *staple = [CDSemanticStringStaple new ];
4058 staple.string = string;
4159 staple.type = type;
42- [_components addObject: staple];
60+
61+ _tail.next = staple;
62+ _tail = staple;
63+
64+ if (_head == nil ) {
65+ _head = staple;
66+ }
67+
4368 _length += string.length ;
4469 }
4570}
4671
4772- (BOOL )startsWithChar : (char )character {
4873 char *bytes = &character;
49- NSString *suffix = [[NSString alloc ] initWithBytesNoCopy: bytes length: 1 encoding: NSASCIIStringEncoding freeWhenDone: NO ];
50- return [_components.firstObject. string hasPrefix: suffix ];
74+ NSString *prefix = [[NSString alloc ] initWithBytesNoCopy: bytes length: 1 encoding: NSASCIIStringEncoding freeWhenDone: NO ];
75+ return [_head. string hasPrefix: prefix ];
5176}
5277
5378- (BOOL )endWithChar : (char )character {
5479 char *bytes = &character;
5580 NSString *suffix = [[NSString alloc ] initWithBytesNoCopy: bytes length: 1 encoding: NSASCIIStringEncoding freeWhenDone: NO ];
56- return [_components.lastObject .string hasSuffix: suffix];
81+ return [_tail .string hasSuffix: suffix];
5782}
5883
5984- (void )enumerateTypesUsingBlock : (void (NS_NOESCAPE ^)(NSString *string, CDSemanticType type))block {
60- for (CDSemanticStringStaple *staple in _components ) {
85+ for (CDSemanticStringStaple *staple = _head; staple != nil ; staple = staple. next ) {
6186 block (staple.string , staple.type );
6287 }
6388}
6489
6590- (void )enumerateLongestEffectiveRangesUsingBlock : (void (NS_NOESCAPE ^)(NSString *string, CDSemanticType type))block {
6691 CDSemanticType activeStapleType = CDSemanticTypeStandard;
6792 NSMutableString *concatString = nil ;
68- for (CDSemanticStringStaple *staple in _components ) {
93+ for (CDSemanticStringStaple *staple = _head; staple != nil ; staple = staple. next ) {
6994 if ((concatString == nil ) || (staple.type != activeStapleType)) {
7095 if (concatString != nil ) {
7196 block ([concatString copy ], activeStapleType);
@@ -83,7 +108,7 @@ - (void)enumerateLongestEffectiveRangesUsingBlock:(void (NS_NOESCAPE ^)(NSString
83108
84109- (NSString *)string {
85110 NSMutableString *build = [NSMutableString string ];
86- for (CDSemanticStringStaple *staple in _components ) {
111+ for (CDSemanticStringStaple *staple = _head; staple != nil ; staple = staple. next ) {
87112 [build appendString: staple.string];
88113 }
89114 return [build copy ];
0 commit comments