jQuery模块函数意外返回'未捕获的类型错误'

jQuery module function is unexpectedly returning 'Uncaught TypeError'?

本文关键字:类型 错误 返回 函数 jQuery 模块 意外      更新时间:2023-09-26

我正在尝试使用模块模式来构建一个搜索函数:

https://learn.jquery.com/code-organization/concepts/

 $("#search").click(function(){
        var searchFunc = (function(){   
            event.preventDefault();     
            var term = $("#searchInput").val();
            var warning = $('#searchErrors');
            var regex = /^[a-zA-Z0-9'-'s]+$/;
            var keyboard = $(':focus');
            var error = null;
            var validateTerm = function(term){
                if (term === ''){
                    var error = 'Please enter a search term';
                }
                else if (!regex.test(term)){
                    var error = 'Please enter only alphanumeric characters (numbers and letters).';
                }
                return error;
            };
            var displayErrors = function(error){
                warning.append(error).show();
            };
            keyboard.blur();
        })();
        searchFunc.validateTerm(term);
        if (error != null){
            displayErrors.empty();
            searchFunc.displayErrors(error);    
        }
        else{
            return returnResults(term);     
        }
    });
    var returnResults = (function(term) {
        console.log(term);
    })();

当运行时,我得到这个错误:

script.js:28未捕获类型错误:无法读取属性"validateTerm"未定义

我正在单击带有空白#searchInput字段的#search按钮,期望searchFunc验证该术语,然后显示#searchErrorsdiv并在其后面附加我的错误消息。是什么导致了此错误?

上面的代码中没有任何内容会A)使searchTerm不是undefined,或者B)使其具有validateTerm属性(如果是的话)。分配给searchTerm时调用的函数不会返回任何内容,因此调用它会导致undefined。在函数内声明变量并不能使该变量在函数外可访问(幸运的是)。

我不知道你想用你的代码做什么,但模块模式基本上是这样的(使用ES5和更早的版本):

var thing = (function() {
    function foo() {
    }
    function bar() {
    }
    return {
        foo: foo
    };
})();

关键事项:

  1. 我们返回一些东西,通常是一个对象

  2. 我们为该对象分配属性,以揭示"模块"(作用域函数)之外的内容。

其他编队:

var thing = (function() {
    function bar() {
    }
    return {
        foo: function foo() {
        }
    };
})();

var thing = (function() {
    var t = {};
    function bar() {
    }
    t.foo = function foo() {
    };
    return t;
})();

或者使用ES2015(目前你仍然需要转基因才能在野外使用ES2015):

var thing = (function() {
    function bar() {
    }
    return {
        foo() {
        }
    };
})();

所有这些都导致thing引用一个对象(我们在return上使用对象初始化器创建的对象),属性foo引用foo函数,以及一个只有foo才能访问的完全私有的bar函数。

对不起,我上面的评论(可能)不正确。

在validateTerm函数中,您在每个if块中定义了"error"——在if块之外无法访问它。

如果在If语句之外定义错误,它将正确返回。(为了清楚起见,我将其重命名为returnError,这样你就可以看到上面定义的错误和你的函数中的错误之间的区别。)

var validateTerm = function(term){
            var returnError = "";
            if (term === ''){
                returnError = 'Please enter a search term';
            }
            else if (!regex.test(term)){
                returnError = 'Please enter only alphanumeric characters (numbers and letters).';
            }
            return returnError;
        };

此外,我可以看到你之前已经定义了"错误",所以我猜你想修改验证行如下:-

error = searchFunc.validateTerm(term);

当您想将函数返回的值分配给以后使用的错误变量时。