【问题标题】:Javascript objects with properties that are functions details about 'this'Javascript 对象的属性是关于“this”的详细信息
【发布时间】:2012-07-04 20:37:24
【问题描述】:
var foo = {
  p1: function(){
    return this.p2;
  },

  p2: function(){
    console.log('i am foo.p2');
  }
};

我正在尝试执行与上面的示例类似的操作,但是在调用时遇到了一个问题:

var result = foo.p1();

结果 == '未定义'

我对“this”在对象上下文中的工作方式感到困惑。有人能解释一下我哪里出错了吗?

编辑 更完整的例子:

suite_segments.themis = {

    //don't re-run themis initialization script
    initialized: false,

    /**
     * Initializer for themis product. Returns true if initialization
     * operations were performed, false if not (most likely because 
     * the product was already initialized -- not a fresh navigation)
     */
    init: function(){

            //prevent multiple initializations
            if(this.initialized)
                return false; //did not initialize
            this.initialized = true;

            //operations
            jQuery('#tabs').tabs();


            //init success
            return this.themis_destroy;         
    },





    /* ----------------------------------------------------------------------------------
     *      DESTRUCTORS
     * ----------------------------------------------------------------------------------/
    /**
     * Function to be invoked if user navigates away from 'themis' entirely. Other
     * sub-destroy type functions will be invoked if necessary when a user switches 
     * between parts of themis
     * 
     */
    themis_destroy: function(){

        console.log('themis_destructor');
        this.initialized = false;

    },
    /**
     * Designed to be overwritten every time a segment of themis is loaded. Will be invoked 
     * ever time a segment of themis is loaded.
     */
    themis_sub_destroy: function(){}


};

【问题讨论】:

  • 发布您正在尝试的实际代码或创建fiddle
  • foo.p1() 确实产生了foo.p2。发布更完整的sn-p。
  • 我不知道,伙计,你的 sn-p 实际上在 JSFiddle 中工作。 suite_segments.themis.init(); 真的返回 suite_segments.themis.themis_destroy。一定有别的东西。

标签: javascript object scope this


【解决方案1】:

您完成的示例也可以正常工作。使用您的代码,suite_segments.themis.init() 返回析构函数(或 false),而不是 undefined

但是您还有另一个问题:析构函数不起作用。阅读this excellent overview about the this keyword,您会看到:this 指向当前上下文,该上下文依赖于调用。当根据...themis.init() 调用时,该函数将在themis 对象的上下文中调用——一切都很好。但是返回的函数 (suite_segments.themis.destroy) 不会在对象上调用,而是(我猜)是独立的 - 并且没有机会设置正确对象的 initialized 属性。

在你的情况下,我可以推荐.bind() method 来设置返回函数的上下文:

return this.themis_destroy.bind(this);

另请参阅this blog post about "objects with properties that are functions" or the mythof of methods,它完全涵盖了您的标题问题,以及this post about this

【讨论】:

    【解决方案2】:

    Doug Crockford 在对象中有一个很好的page about private/public/privileged members,并讨论了定义这些成员的最佳实践。这可能有助于消除您对 this 变量的一些困惑。

    但是,在您的示例中,您不能向我们展示一些东西。 foo.p1 的返回值是函数foo.f2 如下所示:

    http://jsfiddle.net/erSWu/1/

    【讨论】:

    • 虽然通过使用构造函数给对象私有“成员”可以解决 OPs 问题,但如果没有进一步的解释,那篇文章是完全没用的,尤其是在 this 关键字上(文章确实这样做了 澄清)
    【解决方案3】:

    兄弟,你犯了一个矿工错误……

    应该是这样的:

    var foo = {
      p1: function(){
        return this.p2();
      },
    
      p2: function(){
        console.log('i am foo.p2');
      }
    };
    

    【讨论】:

    • 不,那个会返回undefined,因为foo.p2不会返回任何东西。
    • 这不是凯西想要的。他希望返回对foo.p2引用,因为在他更详细的sn-p 中foo.p2 是稍后调用的析构函数。
    猜你喜欢
    • 1970-01-01
    • 2017-08-01
    • 2012-03-19
    • 1970-01-01
    • 1970-01-01
    • 2013-10-10
    • 1970-01-01
    • 2020-02-25
    • 1970-01-01
    相关资源
    最近更新 更多