Javascript 范围——var vs global

Posted

技术标签:

【中文标题】Javascript 范围——var vs global【英文标题】:Javascript scope -- var vs global 【发布时间】:2013-04-11 21:47:19 【问题描述】:

对于currentUnknownBox,如果我使用“var”,预期的功能将无法按预期工作(currentUnknownBox 成为单击的第一个元素)。如果我删除 var,它会按预期工作。我假设这与全局范围有关。有人可以向我解释一下吗?

jQuery(".box.unknown").live('click',function()

    var currentUnknownBox = this;

    //if we are NOT on mobile, use jQuery UI dialog
    if (!Drupal.settings.is_mobile)
    
        jQuery("#letter-input-dialog").dialog();

        jQuery('#letter_input_form').submit(function()
        
            var letter = jQuery("#letter_input").val();
            jQuery("#letter-input-dialog").dialog('close');
            jQuery("#letter_input").val('');
            that.validateAndSaveLetter(currentUnknownBox, letter);
            //Do not let the form actually submit
            return false;
        );
    
    else
    
        var letter = prompt('Please enter a letter to use in your guess');
        that.validateAndSaveLetter(that.currentUnknownBox, letter);
    
);

编辑: 问题是我每次都在重新声明我的提交函数。

【问题讨论】:

that 定义在哪里? currentUnknownBox 好像没问题,但that 是什么?为什么that 变量上还有一个currentUnknownBox 属性(在else 子句中预期)? 与您的问题无关,但在 JS 花括号位置很重要,可能不应该在他们自己的行:***.com/questions/3641519/… @ZachL:这仅适用于对象文字。你放大括号的地方是个人编码风格,(虽然我不喜欢)Allman style 很好 @Bergi 是的,但保持一致很重要,因此即使是很小的边缘情况(这不是)也足以成为不使用 Allman 风格 IMO 的理由。 【参考方案1】:

您忘记声明 var 'that'。 我认为你需要在'if'语句之前这样做

var that = this;

【讨论】:

在哪里?我看不到你在哪里重新声明。 见Dan's answer。这段代码:jQuery('#letter_input_form').submit(function() ... 每次点击 .box.unknown 时都会运行,将新的事件处理程序添加到 #letter_input_form 是的,真的。无论如何,.live 已弃用。【参考方案2】:

每当您使用var 时,您都在声明变量的范围。如果你省略它,那么 javascript 会假定最兼容的选项是全局的。技术术语是“hoisting”。更准确地说,JavaScript 具有所谓的函数作用域,因此即使您在 for 循环中声明变量,JavaScript 也会将其“提升”到最近的函数的顶部。

【讨论】:

【参考方案3】:

问题在于,每次单击其中一个时,您都会向表单添加一个 new 提交事件处理程序。但第一个总是先开火。当您不声明 var 时,您将覆盖第一个处理程序正在查看的变量。但错误是每次都添加一个新的处理程序。我会这样做:

var currentUnknownBox;
jQuery('#letter_input_form').submit(function()
    
        var letter = jQuery("#letter_input").val();
        jQuery("#letter-input-dialog").dialog('close');
        jQuery("#letter_input").val('');
        that.validateAndSaveLetter(currentUnknownBox, letter);
        //Do not let the form actually submit
        return false;
    );
jQuery("#letter-input-dialog").dialog(autoOpen: false);

jQuery(".box.unknown").live('click',function()
    currentUnknownBox = this;

    //if we are NOT on mobile, use jQuery UI dialog
    if (!Drupal.settings.is_mobile)
     
       jQuery("#letter-input-dialog").dialog('open');
       else 
        var letter = prompt('Please enter a letter to use in your guess');
       that.validateAndSaveLetter(currentUnknownBox, letter);
         
);

顺便提一下,.live 已被弃用。你应该改用.on

【讨论】:

以上是关于Javascript 范围——var vs global的主要内容,如果未能解决你的问题,请参考以下文章

javascript中的let vs var [重复]

超出范围时的 JavaScript 画布裁剪形状

javascript JavaScript范围 - Var

JavaScript中的var functionName = function() vs function functionName()

var functionName = function() vs function functionName()

var functionName = function() vs function functionName()