【问题标题】:JavaScript: How to set a property for a function?JavaScript:如何为函数设置属性?
【发布时间】:2011-04-26 14:04:07
【问题描述】:

我正在测试我的一个函数,我想测试是否使用该代码中的正确参数调用了特定函数。

因此,我像这样覆盖原来的函数:

var oldSort = sort;
sort = function(array) {
    this.arrayToSort = array;
}

然后我执行它并检查属性sort.arrayToSort是否设置为我传入的值并重新分配原始函数:

sort(myArray);
deepEqual(myArray, sort.arrayToSort); 
sort = oldSort;

但是,我无法像那样访问sort.arrayToSort。如何设置函数的属性以使其成为可能?现在,我在 sort 函数上方声明一个变量并对其进行设置,但我宁愿将其作为函数的属性以保持其范围较小。这可能吗?

【问题讨论】:

  • 这是你自己的 deepEqual 函数还是你使用了一些 javascript 库?什么线路导致问题?您能否包含完整的 javascript 而不是这两个 sn-ps。
  • 我正在使用 QUnit,这是一个测试用例。我写了这个 sn-p 来重现我在生产系统中遇到的一个问题,我无法发布它的代码。

标签: javascript unit-testing function properties mocking


【解决方案1】:

听起来你想要arguments.callee,它指的是函数本身,而不是它所绑定的对象。

var oldSort = sort;
sort = function(array) {
    arguments.callee.arrayToSort = array;
}

【讨论】:

  • 太好了,这行得通!但它确实看起来有点晦涩 - 在我的情况下你会建议这样做吗?
  • 另一种方法是直接引用排序(sort.arrayToSort = array)。 arguments.callee 是在匿名函数上执行此操作的唯一方法。
  • 我不知道是否有支持模拟全局函数的 JS 模拟库,但这基本上就是你想要做的。如果你能找到使用模拟库的方法,我会推荐。
  • 是的,我正在尝试在这里模拟一个全局函数,但我不确定是否要添加第 3 方模拟框架。
  • 我想我要么保持原样,要么引入 Sinon.JS,似乎与 QUnit 配合得很好。无论如何,你回答了我的问题,所以我会接受:)
【解决方案2】:

如果你不使用 new 关键字创建函数属性,你将无法访问它。

mysort = new sort(array);
alert(mysort.arrayToSort);

您可以在原始排序中使用自定义比较器功能。像这样

array.sort(sortfunction)

function sortfunction(a, b){
   //Compare "a" and "b" in some fashion, and return -1, 0, or 1
}

【讨论】:

  • 同样有效,但同样晦涩难懂。正如我问奥斯汀:你会建议我这样做吗?
  • 我只是不明白为什么要覆盖原始排序?您可以编写自己的排序函数并将其作为参数传递给排序。我会更新我的帖子以说明清楚。
  • 对不起,我猜这个例子很糟糕,我假设排序函数是我定义的。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-09-20
  • 1970-01-01
  • 2012-12-04
  • 1970-01-01
  • 1970-01-01
  • 2019-07-04
相关资源
最近更新 更多