Home  >  Article  >  Web Front-end  >  A brief analysis of Prototype source code String part (1) related to indexOf optimization_prototype

A brief analysis of Prototype source code String part (1) related to indexOf optimization_prototype

WBOY
WBOYOriginal
2016-05-16 17:57:17866browse

添加到String.prototype中的方法比较多,不过归结起来,大致分为下面几类:

分类 方法名 
原始能力增强               strip |  include  |  startsWith  |  endsWith |  empty |  blank
格式 camelize | capitalize |  underscore |  dasherize  | inspect          
变形 toArray |  succ  | times
替换 interpolate  | sub |  scan |  truncate | gsub
HTML处理 stripTags  | escapeHTML |  unescapeHTML
参数序列化 toQueryParams
JSON处理 unfilterJSON |  isJSON |  evalJSON |  parseJSON
脚本处理 stripScripts |  extractScripts  | evalScripts

Starting from the basic original ability enhancement, the following is the specific implementation, which is easy to understand:

Copy code The code is as follows:

(function(s){
function strip(){
return this.replace(/^s /,'').replace(/s $/, '');
}
function include(pattern){
return this.indexOf(pattern) > -1;//split
}
function startsWith(pattern) {
return this.lastIndexOf(pattern, 0) === 0;
}
function endsWith(pattern) {
var d = this.length - pattern.length;
return d >= 0 && this.indexOf(pattern, d) === d;
}
function empty() {
return this == '';
}
function blank() {
return /^s*$/.test(this);
}
s.strip = String.prototype.trim || strip;
s.include = include;
s.startsWith = startsWith;
s.endsWith = endsWith;
s.empty = empty;
s.blank = blank;
})(String.prototype);

The strip above is $.trim in jquery, and most of them seem to be trim. The tragedy of directly extending the native prototype is revealed here, because the trim method is implemented in subsequent JS implementations (such as chrome), which is self-defeating.
Copy code The code is as follows:

function strip(){
return this.replace (/^s /,'').replace(/s $/,'');
}

The replace(/^s /,'') here is trimLeft, replace(/s $/,'') is trimRight, but these two methods are not available in Prototype.String.

The following is the more interesting part of this part:

When I was watching this paragraph, I was very confused about startsWith and endsWith. Logically speaking, indexOf can be used for startsWith. Here lastIndexOf is used. Later, I checked the implementation of Prototype1.6 version:
Copy the code The code is as follows:

function startsWith(pattern) {
return this.indexOf(pattern) === 0;
}

function endsWith(pattern) {
var d = this.length - pattern.length ;
return d >= 0 && this.lastIndexOf(pattern) === d;
}

It can be seen that startsWith used indexOf in the previous version, but it was modified in version 1.7 The implementation of startsWith. In version 1.7:

In the implementation of startsWith, lastIndexOf searches from back to front, but the starting point (fromindex) is set to 0, so you only need to detect the beginning once.
In the endsWith implementation, indexOf searches from front to back. Since the length of the string is variable, the length is calculated here, and then the starting point (fromindex) is determined, so the end only needs to be detected once.

The performance optimization here is that in the 1.6 implementation, if there is no match at the beginning (that is, startsWith is not established), indexOf will still search backward until it finds a match or the end of the string, which is a waste . For example, for the following operation:

'abcdefgabcdefg'.startsWith('abc')
In the implementation of version 1.6 and version 1.7, there is no difference, but let's convert it:

'abcdefgabcdefg'.startsWith('xesam')
In the 1.6 implementation, the indexOf operation inside startsWith will continue after the a at the beginning does not match x. Although there is no need to continue, the indexOf will still continue. Search backward until a matching 'xesam' is found or until the end of the string.
In the 1.7 implementation, lastIndexOf inside startsWith is searched in reverse (fromIndex=0), so after the beginning a does not match x, the operation stops because lastIndexOf has reached the end.
In this comparison, if the string to be detected is very long, there will be a significant difference in the efficiency of the two implementation methods.
The principle of endsWith is the same.
Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn