【问题标题】:Equivalent of try...catch as an expression等价于 try...catch 作为表达式
【发布时间】:2020-12-19 01:17:08
【问题描述】:

我正在寻找一种方法来做类似的事情:

myVar = try {someFunction();} catch (e) {return undefined;} ?? defaultValue;

我知道这是不正确的,但你明白了。我只是想知道是否有一种优雅的方法可以做到这一点?

【问题讨论】:

  • 没有。如果必须,您可以使用 IIFE。还有一个(尚未正式)proposal

标签: javascript function try-catch expression metaprogramming


【解决方案1】:

实施例如afterThrowing method modifier 可能会导致表达式与 OP 的伪代码一样短且接近 ...

const value = try {someFunction();} catch (e) {return undefined;} ?? defaultValue;

...然后会变成...

const value = (someFunction.afterThrowing(() => null)()) ?? defaultValue;

...实现和示例代码作为概念证明...

// myVar = try {someFunction();} catch (e) {return undefined;} ?? defaultValue;

function throwError() {
  throw (new Error('invocation failure'));
}
function getDate() {
  return Date.now();
}
const defaultValue = '... did throw.'

// expressions as short and as close as one can get
// to what has been ask for ...
//
console.log(
  (getDate.afterThrowing(() => null)()) ?? defaultValue
);
console.log(
  (throwError.afterThrowing(() => null)()) ?? defaultValue
);


// demonstrate capability of the after throwing handler ...
function afterThrowingHandler(error, args) {
  console.log(
    'afterThrowingHandler :: context, error, argsList :',
    this,
    error.toString(),
    Array.from(args)
  );
  return null; // according to the OP's use case.
}

console.log(
  (getDate.afterThrowing(afterThrowingHandler)()) ?? defaultValue
);

console.log(
  (throwError.afterThrowing(

    afterThrowingHandler,
    { biz: 'buzz' }

  )('foo', 'bar', 'baz')) ?? defaultValue
);
.as-console-wrapper { min-height: 100%!important; top: 0; }
<script>
  (function (Function) {

    const fctPrototype = Function.prototype;
    const FUNCTION_TYPE = (typeof Function);

    function isFunction(type) {
      return (
           (typeof type == FUNCTION_TYPE)
        && (typeof type.call == FUNCTION_TYPE)
        && (typeof type.apply == FUNCTION_TYPE)
      );
    }
    function getSanitizedTarget(target) {
      return ((target != null) && target) || null;
    }

    function afterThrowing/*Modifier*/(handler, target) {
      target = getSanitizedTarget(target);

      const proceed = this;
      return (

        isFunction(handler) &&
        isFunction(proceed) &&

        function () {
          const context = target || getSanitizedTarget(this);
          const args = arguments;

          let result;
          try {
            result = proceed.apply(context, args);

          } catch (exception) {

            result = handler.call(context, exception, args);
          }
          return result;
        }

      ) || proceed;
    }
    // afterThrowing.toString = () => 'afterThrowing() { [native code] }';

    Object.defineProperty(fctPrototype, 'afterThrowing', {
      configurable: true,
      writable: true,
      value: afterThrowing/*Modifier*/
    });

  }(Function));
</script>

我不介意有一天,JavaScript 会正式推出... Function.prototype[before|after||around|afterThrowing|@987654327 ].

【讨论】:

    【解决方案2】:

    函数式try catch

    const tryF = (func) => {
      try {
        return func();
      } catch (e) {
        return null;
      }
    };
    

    然后使用

    Const val = tryF(() => dosomething ())
    

    【讨论】:

      【解决方案3】:

      你目前能做的最好的可能是 IIFE:

      myVar = (() => {
        try {
          return someFunction();
        } catch (e) {
        }
      })() ?? defaultValue;
      

      【讨论】:

      • 异常情况下的返回值是多少?
      • 在这种情况下,不返回任何内容,因此默认为undefined
      猜你喜欢
      • 1970-01-01
      • 2019-09-09
      • 2019-11-15
      • 2011-04-15
      • 1970-01-01
      • 2015-02-21
      • 2012-01-07
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多