JavaScript Promise函数风格

4
假设我有一个基于某些需要先计算的输入值的函数,将返回一个 Promise。看起来有两种方法可以实现这个功能。 示例 1:

function foo(val) {
  var newVal = val + 100;
  var anotherVal = newVal % 12;
  var returnVal = anotherVal * 3;

  return new Promise(function(resolve, reject) {
    setTimeout(function() {
      resolve(returnVal);
    }, 1000);      
  });
}

foo(10).then(function(val) {
  console.log(val);
});

例子 2:

function foo(val) {
  return new Promise(function(resolve, reject) {
    var newVal = val + 100;
    var anotherVal = newVal % 12;
    var returnVal = anotherVal * 3;
    setTimeout(function() {
      resolve(returnVal);
    }, 1000);      
  });
}

foo(10).then(function(val) {
  console.log(val);
});

第一个例子将所有设置都放在承诺函数之外。第二个例子将所有逻辑都移至该函数内部。表面上,这些方法在几乎所有情况下似乎是等效的。我想知道是否有人了解其中哪种方法比另一种更好?或者我是否遗漏了其他更好的方法?
谢谢!
2个回答

4
你的两个函数唯一的区别就是变量初始化的位置,唯一的区别是变量作用域。你的两个函数都会从promise返回相同的结果,但是第一个方法可以在函数内部以外访问变量,这是它的优点。

Promise外的变量:

function foo(val) {
  var newVal = val + 100;
  var anotherVal = newVal % 12;
  var returnVal = anotherVal * 3;

  console.log(returnVal); // Returns 6

  return new Promise(function(resolve, reject) {
    setTimeout(function() {
      resolve(returnVal);
    }, 1000);      
  });
}

foo(10).then(function(val) {
  console.log(val);
});

Promise内的变量:

function foo(val) {
  
  console.log(returnVal); // Variable doesn't exist
  
  return new Promise(function(resolve, reject) {
    var newVal = val + 100;
    var anotherVal = newVal % 12;
    var returnVal = anotherVal * 3;
    setTimeout(function() {
      resolve(returnVal);
    }, 1000);      
  });
}

foo(10).then(function(val) {
  console.log(val);
});

因此,这取决于您想如何使用变量。如果您希望在Promise之外利用它们,请选择两个函数中的第一个。如果您知道永远不需要在Promise之外访问这些变量,请在Promise内定义它们以防止变量范围泄漏,从而提高内存。希望这可以帮助您! :)

1
你需要考虑另一个问题,如果在Promise内部有异常,并且该承诺的拒绝没有得到适当处理,则会出现UnhandledPromiseRejectionWarning错误,而在第一种方法中,你只会遇到普通异常。

这是一个很好的观点。我没有考虑到错误处理的方式。 - Alex Bieg
我会为第一段点赞,为第二段点踩 :-) 不,Promise 构造函数的回调也是同步运行的。 - Bergi
@Bergi 你是对的,我已经更新了我的答案。谢谢你指出了这一点。 - Jay

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接