我们在工作中可能会很少进行这样的思考,对于一些常用的原生api它是如何实现的呢,如果让我们去用js实现一个与原生api功能相同的函数我们该如何设计算法去实现呢?

  为了巩固自己的编程技术和提高自己的编程技巧,也为了让自己对js这门语言有更深刻的理解,我将会把平时开发常用到的各种原生api用自己的方式去实现,如果有错误的地方或者代码运行效率有更好的实现方案欢迎大神指正和批评

  本次将要实现的第一个方法是Javascript的String基本类型和String对象的常用方法 slice

  slice的定义和用法 (红色文字部分摘自菜鸟教程,slice方法)

slice(start, end) 方法可提取字符串的某个部分,并以新的字符串返回被提取的部分。

使用 start(包含) 和 end(不包含) 参数来指定字符串提取的部分。

字符串中第一个字符位置为 0, 第二个字符位置为 1, 以此类推。

提示: 如果是负数,则该参数规定的是从字符串的尾部开始算起的位置。也就是说,-1 指字符串的最后一个字符,-2 指倒数第二个字符,以此类推。

start:必须. 要抽取的片断的起始下标。第一个字符位置为 0

end:可选。 紧接着要截取的片段结尾的下标。若未指定此参数,则要提取的子串包括 start 到原字符串结尾的字符串。

  如果该参数是负数,那么它规定的是从字符串的尾部开始算起的位置。

  slice()方法在第一个参数为负数时不管第二个参数为正数还是负数都会返回"";第二个参数为负数时会将负的参数加上字符串的长度。

 var sliceYMWM=function(s,start,end){
// 首先我们的方法得满足大前提,s必须为String类型或者是String对象的实例
if(typeof(s) == 'string' || s instanceof String){
var slen=s.length;
var aglen=arguments.length;
var res="";
// 我们先处理只用两个参数 s 和 start 的情况
if(aglen==2){
if(start>slen){ //此时起始索引大于串长返回空串
return res;
}else if(start>0&&start<slen){
for(let i = start; i<slen; i++){
res+=s[i];
}
return res;
}else{
for(let q = slen+start; q<slen; q++){
res+=s[q];
}
return res;
}
}else if(aglen==3){//当三个参数都有的情况
if(start<0){//第一个参数 start 为负数时,都会返回 ""
return res;
}else{
if(end<0){ //当第三个参数 end 为负数时,需要加串长转换成正序的索引
if(start<end+slen){
for(let j= start; j<end+slen;j++){
res+=s[j];
}
return res;
}else{ //此时起始索引大于等于结束索引返回空串
return res;
}
}else{
if(start<end){ //当结束索引大于串长时,须改良循环结构的退出条件,否则当结束索引远大于串长时会做无用的性能消耗
if(end<slen){
for(let k=start; k<end;k++){
res+=s[k];
}
return res;
}else{
for(let k=start; k<slen;k++){
res+=s[k];
}
return res;
}
}else{ //此时起始索引大于等于结束索引返回空串
return res;
}
}
}
}else{
throw "参数个数不满足要求!";
}
}else{
throw "传入的s并非是字符串类型或者是字符串对象!"; }
}
var s1=new String('倚梦为码!');
var s1_=sliceYMWM(s1,0); //运行结果为 String {"倚梦为码!"}
var s2='倚梦为码!';
64 var s2_=sliceYMWM(s2,0); //运行结果为 "倚梦为码!"
65  var s3_=sliceYMWM(s2,-2); // 运行结果为 "码!"
66   var s4_=sliceYMWM(s2,1,-1) //运行结果为 "梦为码"
 
总结:在用js进行实现slice方法时尤其要注意临界值的判断条件,不能少判断也不能做多余的判断防止算法出现与原生slice方法有结果不一致的情况,而且在进行循环条件时应尽量做到不对全局变量的属性查找之类的操作,因为这种操作的时间复杂度为 O(n) 。

我们可以在第一次对全局变量进行属性访问时将其地址存到一个局部变量中,这样的话只会在第一次进行操作时会对全局变量做属性搜素,往后只需对局部变量进行访问,这时算法复杂度只有 O(1),正所谓的即用即取。有兴趣的小伙伴可以自己做做类似的练习。本文为作者  倚梦为码  原创,欢迎大家观看和转载,若有其他用途请注明出处!谢谢合作!

js原生api之String的slice方法的更多相关文章

  1. ES7前端异步玩法:async/await理解 js原生API妙用(一)

    ES7前端异步玩法:async/await理解   在最新的ES7(ES2017)中提出的前端异步特性:async.await. 什么是async.await? async顾名思义是“异步”的意思,a ...

  2. 使用Node.js原生API写一个web服务器

    Node.js是JavaScript基础上发展起来的语言,所以前端开发者应该天生就会一点.一般我们会用它来做CLI工具或者Web服务器,做Web服务器也有很多成熟的框架,比如Express和Koa.但 ...

  3. js中的splice方法和slice方法简单总结

    slice:是截取用的 splice:是做删除 插入 替换用的 slice(start,end): 参数: start:开始位置的索引 end:结束位置的索引(但不包含该索引位置的元素) 例如: va ...

  4. js原生API妙用(一)

    复制数组 我们都知道数组是引用类型数据.这里使用slice复制一个数组,原数组不受影响. let list1 = [1, 2, 3, 4]; let newList = list1.slice(); ...

  5. SpringMVC(八):使用Servlet原生API作为Spring MVC hanlder方法的参数

    在SpringMVC开发中,是有场景需要在Handler方法中直接使用ServletAPI. 在Spring MVC Handler的方法中都支持哪些Servlet API作为参数呢? --Respo ...

  6. js在IE8+兼容String没有trim方法,写一个兼容ie8一下的浏览器的trim()方法

    方法一: String.prototype.trim = function(){ return Trim(this);}; function LTrim(str) {    var i;     fo ...

  7. JS支持正则表达式的 String 对象的方法

    注意:本文中所有方法的 RegExp 类型的参数,其实都支持传入 String 类型的参数,JS会直接进行字符串匹配. (相当于用一个简单的非全局正则表达式进行匹配,但字符串并没有转换成 RegExp ...

  8. js原生设计模式——4安全的工厂方法模式之Factory方法模式

    <!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8&qu ...

  9. JS 的 Array 和String 常混淆方法

    知识一: 1.slice() 提取字符串 slice[ start, end) 如果参数为负数,表示从尾部开始算起. 2.subString() 提取字符串 3.subStr() 提取字符串 subS ...

随机推荐

  1. 域名系统(DNS)

    DNS (domain name server/system) 1.基本信息 网络中数据通信依赖ip地址 测试:手动将dns服务地址改为空值,通过ip和域名分别测试网络的联通性 FQDN 完全域名(完 ...

  2. vim+astyle安装使用

    astyle下载安装 wget https://sourceforge.net/projects/astyle/files/astyle/astyle%203.1/astyle_3.1_linux.t ...

  3. Ubuntu14.04 Anaconda

    我虚拟机Ubuntu14.04上的Python已经存在了两个版本,一个是python 2.7,一个是Python 3.4.想在它上面安装Anaconda,但又有所顾虑.我先想到的是,先卸载Ubuntu ...

  4. C 语言预编译 #if #else

    这个方法我一般用来调试的时候用,有时候串口打印信息太多,一条条注释就很麻烦,于是就用这种方法,定义个宏变量,判断宏变量的条件,来达到改变宏变量的值控制那些代码编译,那些不编译的目的,这样就不用一条条代 ...

  5. POSIX 线程编程(二)线程建立与终止

    创建与终止线程 线程的管理常用的API有: pthread_create(thread,attr,start_routine,arg) pthread_exit(status) pthread_can ...

  6. mysql开发之---每日一得01

    2015年7月7日------------------------- 1.truncate表会清空建表语句auto_increment的值:某个表的id即是主键也是自增,你能够选择插入随意id值,假设 ...

  7. ARP协议(3)ARP编程--winpcap&amp;vs2012配置

    好.之前说了那么多.最终到了,我们能够操刀的时候了. 在对ARP协议编程前.我们必需要能控制网络适配器(网卡).这个部分就是驱动! "我们要编写网卡驱动?",对,可是,至少我们现阶 ...

  8. HDU1312 / POJ1979 / ZOJ2165 Red and Black(红与黑) 解题报告

    题目链接:pid=1312" target="_blank">HDU1312 / POJ1979 / ZOJ2165 Red and Black(红与黑) Red ...

  9. 稀疏编码(Sparse Coding)的前世今生(二)

    为了更进一步的清晰理解大脑皮层对信号编码的工作机制(策略),须要把他们转成数学语言,由于数学语言作为一种严谨的语言,能够利用它推导出期望和要寻找的程式.本节就使用概率推理(bayes views)的方 ...

  10. MFC窗口去边框、置顶、全屏、激活

    静态移除长提边框非常easy,直接设置"Border"属性为"none"就可以 "Maximize Box", "Minimize ...