如何在 JavaScript 中从字符串创建函数?
在 JavaScript 中从字符串创建函数在您需要动态地在运行时生成函数或当您拥有包含您希望执行的函数代码的字符串时非常有用。
从字符串构建函数的能力是 JavaScript 的一项有用功能,它允许在运行时动态创建函数。`eval()` 函数和 `new Function()` 函数对象是执行此操作的两种最常用的方法,尽管两者都存在重大的安全漏洞。
即使 `Function.prototype.constructor` 不太为人所知,它也是一个更安全的选项。在选择用于从字符串创建 JavaScript 函数的方法之前,务必考虑风险和用例。
方法 1:使用 `eval()` 函数
JavaScript `eval()` 方法是从字符串构建函数的最简单方法之一。此强大的 `eval()` 函数可以运行作为字符串提供给它的任何 JavaScript 代码。
示例
<html>
<body>
<p id="result"></p>
<script>
let functionString = "function add(a, b) { return a + b; }";
let add = eval("(" + functionString + ")");
document.getElementById("result").innerHTML = "Sum of 1 and 2: " + add(1, 2);
</script>
</body>
</html>
在这里我们可以看到,我们有一个函数,它接受两个参数并返回它们的和。现在,此函数包含在一个字符串中。`eval()` 函数接收此字符串作为参数并对其进行评估,然后返回该函数。然后将返回的函数分配给名为 `add` 的变量,该变量可以像任何其他函数一样使用。
但是,它会运行提供给它的任何 JavaScript 代码,因此在生产代码中使用它可能存在风险,因为它可能导致安全漏洞。
方法 2:使用 `new Function()` 构造函数
在 JavaScript 中从字符串创建函数的另一种方法是使用 `Function()` 构造函数。`Function()` 构造函数从包含函数代码的字符串创建一个新的函数对象。以下是如何使用 `Function()` 构造函数从字符串创建函数的示例:
示例
<html>
<body>
<p id="print"></p>
<script>
let functionString = "function add(a, b) { return a + b; }";
let functionBody = functionString.substring(
functionString.indexOf("{") + 1,
functionString.lastIndexOf("}")
);
let add = new Function("a", "b", functionBody);
document.getElementById("print").innerHTML = "Sum of 1 and 2: " + add(1, 2);
</script>
</body>
</html>
在此示例中,我们将包含函数代码的字符串传递给 `Function()` 构造函数,该构造函数从此字符串创建一个新的函数对象。然后我们将返回的函数分配给变量 `add`,该变量可以像任何其他函数一样使用。
由于它只能创建函数,因此比 `eval()` 风险更小,但仍然存在类似的风险。
方法 3:使用 `Function.prototype.constructor`
这会生成一个函数,并且除了作为字符串传递的函数体之外,不能运行任何其他代码。但是,它使用频率较低,并且与其他两种方法相比,较旧的浏览器对其支持不佳。
示例
<html>
<body>
<p id="result"></p>
<script>
let add = Function.prototype.constructor('a', 'b', 'return a+b')(1, 2);
document.getElementById("result").innerHTML = "Sum: " + add;
</script>
</body>
</html>
在此示例中,向构造函数提供函数参数和函数体。我们使用 `Function.prototype.constructor` 创建一个具有给定参数和给定函数体的函数,然后通过使用给定参数调用该函数来立即调用该函数。
请记住,您从字符串构建的函数将能够访问全局作用域,并且不会包含在您创建它的代码的作用域内。
另一件需要牢记的重要事项是从字符串创建函数可能会减慢应用程序的速度,尤其是在函数体很长的情况下。
此外,如果函数很复杂,从字符串构建函数可能会使理解和调试代码变得更加困难。
由于其安全问题,通常不建议在生产代码中使用 `eval()` 和 `new Function()` 方法。相反,您应该考虑其他选项,例如预编译函数或使用 JavaScript 预处理器(如 Babel)将您的代码转换为等效的安全版本。
数据结构
网络
关系数据库管理系统
操作系统
Java
iOS
HTML
CSS
Android
Python
C 编程
C++
C#
MongoDB
MySQL
Javascript
PHP