Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(111)

Side by Side Diff: src/string.js

Issue 5708006: Optimizing BuildResultFromMatchInfo, StringReplace and StringSplit. (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 10 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« src/regexp.js ('K') | « src/regexp.js ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2006-2009 the V8 project authors. All rights reserved. 1 // Copyright 2006-2009 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after
201 %_Log('regexp', 'regexp-replace,%0r,%1S', [search, subject]); 201 %_Log('regexp', 'regexp-replace,%0r,%1S', [search, subject]);
202 if (IS_FUNCTION(replace)) { 202 if (IS_FUNCTION(replace)) {
203 if (search.global) { 203 if (search.global) {
204 return StringReplaceGlobalRegExpWithFunction(subject, search, replace); 204 return StringReplaceGlobalRegExpWithFunction(subject, search, replace);
205 } else { 205 } else {
206 return StringReplaceNonGlobalRegExpWithFunction(subject, 206 return StringReplaceNonGlobalRegExpWithFunction(subject,
207 search, 207 search,
208 replace); 208 replace);
209 } 209 }
210 } else { 210 } else {
211 return StringReplaceRegExp(subject, search, replace); 211 return %StringReplaceRegExpWithString(subject,
212 search,
213 TO_STRING_INLINE(replace),
214 lastMatchInfo);
212 } 215 }
213 } 216 }
214 217
215 // Convert the search argument to a string and search for it. 218 // Convert the search argument to a string and search for it.
216 search = TO_STRING_INLINE(search); 219 if (!IS_STRING(search)) search = NonStringToString(search);
217 var start = %StringIndexOf(subject, search, 0); 220 var start = %StringIndexOf(subject, search, 0);
218 if (start < 0) return subject; 221 if (start < 0) return subject;
219 var end = start + search.length; 222 var end = start + search.length;
220 223
221 var builder = new ReplaceResultBuilder(subject); 224 var builder = new ReplaceResultBuilder(subject);
222 // prefix 225 // prefix
223 builder.addSpecialSlice(0, start); 226 builder.addSpecialSlice(0, start);
224 227
225 // Compute the string to replace with. 228 // Compute the string to replace with.
226 if (IS_FUNCTION(replace)) { 229 if (IS_FUNCTION(replace)) {
227 builder.add(replace.call(null, search, start, subject)); 230 builder.add(%_CallFunction(%GetGlobalReceiver(),
231 search,
232 start,
233 subject,
234 replace));
228 } else { 235 } else {
229 reusableMatchInfo[CAPTURE0] = start; 236 reusableMatchInfo[CAPTURE0] = start;
230 reusableMatchInfo[CAPTURE1] = end; 237 reusableMatchInfo[CAPTURE1] = end;
231 replace = TO_STRING_INLINE(replace); 238 if (!IS_STRING(replace)) replace = NonStringToString(replace);
Lasse Reichstein 2010/12/13 09:29:13 Is this really faster than the macro: macro TO_ST
sandholm 2010/12/13 12:03:35 No, not really. I reverted this change.
232 ExpandReplacement(replace, subject, reusableMatchInfo, builder); 239 ExpandReplacement(replace, subject, reusableMatchInfo, builder);
233 } 240 }
234 241
235 // suffix 242 // suffix
236 builder.addSpecialSlice(end, subject.length); 243 builder.addSpecialSlice(end, subject.length);
237 244
238 return builder.generate(); 245 return builder.generate();
239 } 246 }
240 247
241 248
242 // Helper function for regular expressions in String.prototype.replace.
243 function StringReplaceRegExp(subject, regexp, replace) {
244 return %StringReplaceRegExpWithString(subject,
245 regexp,
246 TO_STRING_INLINE(replace),
247 lastMatchInfo);
248 }
249
250
251 // Expand the $-expressions in the string and return a new string with 249 // Expand the $-expressions in the string and return a new string with
252 // the result. 250 // the result.
253 function ExpandReplacement(string, subject, matchInfo, builder) { 251 function ExpandReplacement(string, subject, matchInfo, builder) {
254 var next = %StringIndexOf(string, '$', 0); 252 var next = %StringIndexOf(string, '$', 0);
255 if (next < 0) { 253 if (next < 0) {
256 builder.add(string); 254 builder.add(string);
257 return; 255 return;
258 } 256 }
259 257
260 // Compute the number of captures; see ECMA-262, 15.5.4.11, p. 102. 258 // Compute the number of captures; see ECMA-262, 15.5.4.11, p. 102.
(...skipping 308 matching lines...) Expand 10 before | Expand all | Expand 10 after
569 } 567 }
570 568
571 var currentIndex = 0; 569 var currentIndex = 0;
572 var startIndex = 0; 570 var startIndex = 0;
573 var result = []; 571 var result = [];
574 572
575 outer_loop: 573 outer_loop:
576 while (true) { 574 while (true) {
577 575
578 if (startIndex === length) { 576 if (startIndex === length) {
579 result[result.length] = subject.slice(currentIndex, length); 577 result.push(subject.slice(currentIndex, length));
580 break; 578 break;
581 } 579 }
582 580
583 var matchInfo = splitMatch(separator, subject, currentIndex, startIndex); 581 var matchInfo = splitMatch(separator, subject, currentIndex, startIndex);
584 582
585 if (IS_NULL(matchInfo)) { 583 if (IS_NULL(matchInfo)) {
586 result[result.length] = subject.slice(currentIndex, length); 584 result.push(subject.slice(currentIndex, length));
587 break; 585 break;
588 } 586 }
589 587
590 var endIndex = matchInfo[CAPTURE1]; 588 var endIndex = matchInfo[CAPTURE1];
591 589
592 // We ignore a zero-length match at the currentIndex. 590 // We ignore a zero-length match at the currentIndex.
593 if (startIndex === endIndex && endIndex === currentIndex) { 591 if (startIndex === endIndex && endIndex === currentIndex) {
594 startIndex++; 592 startIndex++;
595 continue; 593 continue;
596 } 594 }
597 595
598 result[result.length] = SubString(subject, currentIndex, matchInfo[CAPTURE0] ); 596 result.push(SubString(subject, currentIndex, matchInfo[CAPTURE0]));
Lasse Reichstein 2010/12/13 09:29:13 No special casing of this substring?
sandholm 2010/12/13 12:03:35 I have only inlined SubString calls inside loops.
599 if (result.length === limit) break; 597 if (result.length === limit) break;
600 598
601 var num_captures = NUMBER_OF_CAPTURES(matchInfo); 599 var num_captures_plus3 = NUMBER_OF_CAPTURES(matchInfo) + 3;
Lasse Reichstein 2010/12/13 09:29:13 Use REGEXP_FIRST_CAPTURE instead of 3.
sandholm 2010/12/13 12:03:35 Done.
602 for (var i = 2; i < num_captures; i += 2) { 600 for (var i = 5; i < num_captures_plus3; ) {
Lasse Reichstein 2010/12/13 09:29:13 And REGEXP_FIRST_CAPTURE + 2 instead of 5.
sandholm 2010/12/13 12:03:35 Done.
603 var start = matchInfo[CAPTURE(i)]; 601 var start = matchInfo[i++];
604 var end = matchInfo[CAPTURE(i + 1)]; 602 var end = matchInfo[i++];
605 if (start != -1 && end != -1) { 603 if (end != -1) {
606 result[result.length] = SubString(subject, start, end); 604 if (start + 1 == end) {
605 result.push(%_StringCharAt(subject, start));
606 } else {
607 result.push(%_SubString(subject, start, end));
608 }
607 } else { 609 } else {
608 result[result.length] = void 0; 610 result.push(void 0);
609 } 611 }
610 if (result.length === limit) break outer_loop; 612 if (result.length === limit) break outer_loop;
611 } 613 }
612 614
613 startIndex = currentIndex = endIndex; 615 startIndex = currentIndex = endIndex;
614 } 616 }
615 return result; 617 return result;
616 } 618 }
617 619
618 620
(...skipping 310 matching lines...) Expand 10 before | Expand all | Expand 10 after
929 "small", StringSmall, 931 "small", StringSmall,
930 "strike", StringStrike, 932 "strike", StringStrike,
931 "sub", StringSub, 933 "sub", StringSub,
932 "sup", StringSup, 934 "sup", StringSup,
933 "toJSON", StringToJSON 935 "toJSON", StringToJSON
934 )); 936 ));
935 } 937 }
936 938
937 939
938 SetupString(); 940 SetupString();
OLDNEW
« src/regexp.js ('K') | « src/regexp.js ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698