• Item 20: 使用 call 方法自定义接收者来调用方法


    Item 20: Use call to Call Methods with a Custom
    Receiver
    Ordinarily, the receiver of a function or method (i.e., the value bound
    to the special keyword this ) is determined by the syntax of its caller.
    In particular, the method call syntax binds the object in which the
    method was looked up to this . However, it is sometimes necessary
    to call a function with a custom receiver, and the function may not
    already be a property of the desired receiver object. It’s possible, of
    course, to add the method to the object as a new property:
    obj.temporary = f; // what if obj.temporary already existed?
    var result = obj.temporary(arg1, arg2, arg3);
    delete obj.temporary; // what if obj.temporary already existed?
    But this approach is unpleasant and even dangerous. It is often unde-
    sirable, and even sometimes impossible, to modify obj . Specifically,
    whatever name you choose for the temporary property, you run the
    risk of colliding with an existing property of obj . Moreover, some
    objects can be frozen or sealed, preventing the addition of any new
    properties. And more generally, it’s bad practice to go around arbi-
    trarily adding properties to objects, particularly objects you didn’t
    create (see Item 42).
    Luckily, functions come with a built-in call method for providing a
    custom receiver. Invoking a function via its call method:
    f.call(obj, arg1, arg2, arg3);
    behaves similarly to calling it directly:
    f(arg1, arg2, arg3);
    except that the first argument provides an explicit receiver object.
    The call method comes in handy for calling methods that may have
    been removed, modified, or overridden. Item 45 shows a useful exam-
    ple, where the hasOwnProperty method can be called on an arbitrary
    object, even if the object is a dictionary. In a dictionary object, looking
    up hasOwnProperty produces an entry from the dictionary rather than
    an inherited method:
    dict.hasOwnProperty = 1;
    dict.hasOwnProperty("foo"); // error: 1 is not a function
    Using the call method of the hasOwnProperty method makes it pos-
    sible to call the method on the dictionary even though the method is
    not stored anywhere in the object:
    var hasOwnProperty = {}.hasOwnProperty;
    dict.foo = 1;
    delete dict.hasOwnProperty;
    hasOwnProperty.call(dict, "foo"); // true
    hasOwnProperty.call(dict, "hasOwnProperty"); // false
    The call method can also be useful when defining higher-order func-
    tions. A common idiom for a higher-order function is to accept an
    optional argument to provide as the receiver for calling the function.
    For example, an object that represents a table of key-value bindings
    might provide a forEach method:
    var table = {
    entries: [],
    addEntry: function(key, value) {
    this.entries.push({ key: key, value: value });
    },
    forEach: function(f, thisArg) {
    var entries = this.entries;
    for (var i = 0, n = entries.length; i < n; i++) {
    var entry = entries[i];
    f.call(thisArg, entry.key, entry.value, i);
    }
    }
    };
    This allows consumers of the object to use a method as the callback
    function f of table.forEach and provide a sensible receiver for the
    method. For example, we can conveniently copy the contents of one
    table into another:
    table1.forEach(table2.addEntry, table2);
    This code extracts the addEntry method from table2 (it could have
    even extracted the method from Table.prototype or table1 ), and the
    forEach method repeatedly calls addEntry with table2 as the receiver.
    Notice that even though addEntry only expects two arguments,
    forEach calls it with three: a key, value, and index. The extra index
    argument is harmless since addEntry simply ignores it.
    Things to Remember
    ✦ Use the call method to call a function with a custom receiver.
    ✦ Use the call method for calling methods that may not exist on a given object.

    ✦ Use the call method for defining higher-order functions that allow

    clients to provide a receiver for the callback.

    来源:Effective Javascript编写高质量JavaScript代码的68个有效方法

    progress every day !
  • 相关阅读:
    SQLSTATE[42000]: Syntax error or access violation: 1071 Specified key was too long 解决方法
    Apache Commons 简介
    CSS设置只显示两行文字
    HTML中关于动态创建的标签无法绑定js事件的解决方法:.on()方法的 [.selector]
    AISing Programming Contest 2021(AtCoder Beginner Contest 202)E
    CF620E New Year Tree(dfs序+线段树)
    HDU6955 2021多校 Xor sum(字典树+前缀和异或)
    HDU6959 2021多校 zoto(莫队+分块)
    CF1285D Dr. Evil Underscores(分治)
    CF706D Vasiliy's Multiset(字典树的删除)
  • 原文地址:https://www.cnblogs.com/hghrpg/p/4598975.html
Copyright © 2020-2023  润新知