撩课-Web大前端每天5道面试题-Day17

1.apply, call和bind有什么区别?

三者都可以把一个函数应用到其他对象上,注意不是自身对象.
apply,call是直接执行函数调用,bind是绑定,执行需要再次调用.
apply和call的区别是apply接受数组作为参数,而call是接受逗号分隔的无限多个参数列表.

代码如下:
    function Person() {
    }
    Person.prototype.sayName() { alert(this.name); }

    var obj = {name: 'michaelqin'}; // 注意这是一个普通对象,它不是Person的实例
    1) apply
    Person.prototype.sayName.apply(obj, [param1, param2, param3]);

    2) call
    Person.prototype.sayName.call(obj, param1, param2, param3);

    3) bind
    var liaoke = Person.prototype.sayName.bind(obj);    
    liaoke ([param1, param2, param3]); // bind需要先绑定,再执行 
    liaoke (param1, param2, param3); // bind需要先绑定,再执行

2.defineProperty, hasOwnProperty, isEnumerable都是做什么用的?

Object.defineProperty(obj, prop, descriptor)用来给对象定义属性,
有value,writable,configurable,enumerable,set/get等.hasOwnProerty用于检查某一属性是不是存在于对象本身,继承来的父亲的属性不算.
isEnumerable用来检测某一属性是否可遍历,也就是能不能用for..in循环来取到.

3. js常用设计模式的实现思路,单例,工厂,代理,装饰,观察者模式等?

 1) 单例: 任意对象都是单例,无须特别处理
    var obj = {name: 'michaelqin', age: 30};

 2) 工厂: 就是同样形式参数返回不同的实例
    function Person() { this.name = 'Person1'; }
    function Animal() { this.name = 'Animal1'; }

    function Factory() {}
    Factory.prototype.getInstance = function(className) {
        return eval('new ' + className + '()');
    }

    var factory = new Factory();
    var obj1 = factory.getInstance('Person');
    var obj2 = factory.getInstance('Animal');
    console.log(obj1.name); // Person1
    console.log(obj2.name); // Animal1

 3) 代理: 就是新建个类调用老类的接口,包一下
    function Person() { }
    Person.prototype.sayName = function() { console.log('michaelqin'); }
    Person.prototype.sayAge = function() { console.log(30); }

    function PersonProxy() { 
        this.person = new Person();
        var that = this;
        this.callMethod = function(functionName) {
            console.log('before proxy:', functionName);
            that.person[functionName](); // 代理
            console.log('after proxy:', functionName);
        }
    }

    var pp = new PersonProxy();
    pp.callMethod('sayName'); // 代理调用Person的方法sayName()
    pp.callMethod('sayAge'); // 代理调用Person的方法sayAge() 

 4) 观察者: 就是事件模式,比如按钮的onclick这样的应用.
    function Publisher() {
        this.listeners = [];
    }
    Publisher.prototype = {
        'addListener': function(listener) {
            this.listeners.push(listener);
        },

        'removeListener': function(listener) {
            delete this.listeners[listener];
        },

        'notify': function(obj) {
            for(var i = 0; i < this.listeners.length; i++) {
                var listener = this.listeners[i];
                if (typeof listener !== 'undefined') {
                    listener.process(obj);
                }
            }
        }
    }; // 发布者

    function Subscriber() {

    }
    Subscriber.prototype = {
        'process': function(obj) {
            console.log(obj);
        }
    }; // 订阅者

    var publisher = new Publisher();
    publisher.addListener(new Subscriber());
    publisher.addListener(new Subscriber());
    publisher.notify({name: 'michaelqin', ageo: 30}); // 发布一个对象到所有订阅者
    publisher.notify('2 subscribers will both perform process'); // 发布一个字符串到所有订阅者

4.promise只有2个状态,成功和失败,怎么让一个函数无论成功还是失败都能被调用?

使用promise.all()

Promise.all方法用于将多个Promise实例,包装成一个新的Promise实例。

Promise.all方法接受一个数组作为参数,数组里的元素都是Promise对象的实例,
如果不是,就会先调用下面讲到的Promise.resolve方法,将参数转为Promise实例,再进一步处理。
(Promise.all方法的参数可以不是数组,但必须具有Iterator接口,且返回的每个成员都是Promise实例。)

示例:
var p =Promise.all([p1,p2,p3]);
p的状态由p1、p2、p3决定,分为两种情况。
当该数组里的所有Promise实例都进入Fulfilled状态:Promise.all**返回的实例才会变成Fulfilled状态。
并将Promise实例数组的所有返回值组成一个数组,传递给Promise.all返回实例的回调函数**。

当该数组里的某个Promise实例都进入Rejected状态:
Promise.all返回的实例会立即变成Rejected状态。
并将第一个rejected的实例返回值传递给Promise.all返回实例的回调函数。

5.说说字符串常用的十个函数?

charAt() 返回在指定位置的字符。
concat() 连接字符串。
fromCharCode() 从字符编码创建一个字符串。
indexOf() 检索字符串。
match() 找到一个或多个正则表达式的匹配。
replace() 替换与正则表达式匹配的子串。
search() 检索与正则表达式相匹配的值。
slice() 提取字符串的片断,并在新的字符串中返回被提取的部分。
split() 把字符串分割为字符串数组。
substr() 从起始索引号提取字符串中指定数目的字符。
substring() 提取字符串中两个指定的索引号之间的字符。
toLocaleLowerCase() 把字符串转换为小写。
toLocaleUpperCase() 把字符串转换为大写。
toLowerCase() 把字符串转换为小写。
toUpperCase() 把字符串转换为大写。
toString() 返回字符串。
valueOf() 返回某个字符串对象的原始值。
 
原文地址:https://www.cnblogs.com/gxq666/p/10171946.html