在递归函数中正确处理二维值数组

我正在Apps脚本中实现自定义功能。

要允许该函数在Google表格中用作数组公式,我正在使用以下模板作为该函数:

function myfunction(input) {
  if (input.map) {                // Test whether input is an array.
    return input.map(myfunction); // Recurse over array if so.
  } else {
    // Handle individual values here...
  }
}

这样做可以使自定义函数以二维数组的形式接受范围作为输入,然后返回可以溢出到适当单元格中的二维数组。 This is documented here.

但是,使用下面的代码,我没有使用“输入”,而是使用了“ URL”,我相信这是问题的根源。我产生错误:Attribute provided with no value: url (line 5)

function getRedirect(url) {
  if (url.map) {
    return url.map(getRedirect);
  } else {
    var response = UrlFetchApp.fetch(url,{'followRedirects': false,'muteHttpExceptions': false});
    var redirectUrl = response.getHeaders()['Location']; // undefined if no redirect,so...
    var responseCode = response.getResponseCode();
    if (redirectUrl) {                                   // ...if redirected...
      var nextRedirectUrl = getRedirect(redirectUrl);    // ...it calls itself recursively...
      Logger.log(url + " is redirecting to " + redirectUrl + ". (" + responseCode + ")");
      return nextRedirectUrl;
    } else {                                               // ...until it's not
      Logger.log(url + " is canonical. (" + responseCode + ")");
      return url;
    }
  }  
}

该如何解决?

zzy447845870 回答:在递归函数中正确处理二维值数组

我怀疑您没有正确处理不是有效URL的值。假设脚本没有更多内容,第5行包含UrlFetchApp.fetch()调用,我相信这是错误的根源。

UrlFetchApp.fetch()调用之前和期间,您应该执行其他错误检查。这是一个修改后的实现,展示了我的建议:

function getRedirect(url) {
  if (url.map) {
    return url.map(getRedirect);
  }

  // Return an empty string if url contains a non-string value or an empty string.
  if (typeof url != 'string' || url == '') {
    return '';
  }

  // Enclose the UrlFetchApp.fetch() call in a try/catch() block...
  try {
    var response = UrlFetchApp.fetch(url,{
        'followRedirects': false,'muteHttpExceptions': false
    });
  } catch(e) {
    // And return an empty string if the call fails
    // (e.g. if provided a non-empty,non-URL string).
    return '';
  }

  var redirectUrl = response.getHeaders()['Location'];
  var responseCode = response.getResponseCode();
  if (redirectUrl) {
    var nextRedirectUrl = getRedirect(redirectUrl);
    return nextRedirectUrl;
  }
  return url;
}

一些注意事项:

  • try / catch块之前执行尽可能多的错误检查。在调用UrlFetchApp.fetch()之前处理无效输入要快得多。调用fetch方法并等待其失败可能会花费相当长的时间,尤其是在处理范围较大的情况下。
  • 我删除了日志记录语句,以使示例更加简洁,但是谨慎地记录错误条件和/或返回指出错误的字符串,而不是空字符串。
  • 变量的名称无关紧要(即inputurl
  • 我删除了多余的else块,因为return语句仍然终止了该函数的执行。
本文链接:https://www.f2er.com/3148206.html

大家都在问