Observable.Catch<TSource、TException> 方法 (IObservable<TSource>、Func<TException、IObservable<TSource>>)

使用处理程序生成的可观测序列继续由指定类型的异常终止的可观察序列。

Namespace:System.Reactive.Linq
装配: System.Reactive.dll) 中的 System.Reactive (

语法

'Declaration
<ExtensionAttribute> _
Public Shared Function Catch(Of TSource, TException As Exception) ( _
    source As IObservable(Of TSource), _
    handler As Func(Of TException, IObservable(Of TSource)) _
) As IObservable(Of TSource)
'Usage
Dim source As IObservable(Of TSource)
Dim handler As Func(Of TException, IObservable(Of TSource))
Dim returnValue As IObservable(Of TSource)

returnValue = source.Catch(handler)
public static IObservable<TSource> Catch<TSource, TException>(
    this IObservable<TSource> source,
    Func<TException, IObservable<TSource>> handler
)
where TException : Exception
[ExtensionAttribute]
public:
generic<typename TSource, typename TException>
where TException : Exception
static IObservable<TSource>^ Catch(
    IObservable<TSource>^ source, 
    Func<TException, IObservable<TSource>^>^ handler
)
static member Catch : 
        source:IObservable<'TSource> * 
        handler:Func<'TException, IObservable<'TSource>> -> IObservable<'TSource>  when 'TException : Exception
JScript does not support generic types and methods.

类型参数

  • TSource
    源的类型。
  • TException
    异常的类型。

参数

  • 处理程序 (handler)
    类型: System.Func<TException、 IObservable<TSource>>
    异常处理程序函数,生成另一个可观测序列。

返回值

类型: System.IObservable<TSource>
一个可观测序列,其中包含源序列的元素,后跟处理程序在发生异常时生成的可观测序列生成的元素。

使用说明

在 Visual Basic 和 C# 中,可以在 IObservable<TSource> 类型的任何对象上调用此方法作为实例方法。 当使用实例方法语法调用此方法时,请省略第一个参数。 有关详细信息,请参阅

备注

当发生与处理程序函数中指定的异常类型相同的异常时,可以使用 catch 运算符向订阅引入其他序列。 这是由 Catch 运算符完成的,该运算符执行生成附加序列的异常处理程序。 如果源序列运行到完成时没有异常,则不执行处理程序。 如果遇到的异常与处理程序函数中指定的类型不同,则将该异常发送到观察者的 OnError 处理程序。 本主题中的示例代码演示 Catch 运算符。

示例

以下示例演示了在遇到异常时,如何使用 catch 运算符在订阅中包含其他整数序列。 请注意,引发的异常必须与异常处理程序函数的签名中的异常的类型相同。 如果它不是同一类型,则执行观察程序的 OnError 处理程序,而不是异常处理程序。

using System;
using System.Collections.Generic;
using System.Reactive.Linq;

namespace Example
{

  class Program
  {

    static void Main()
    {
      //***********************************************************************************************//
      //*** sequence1 is generated from the enumerator returned by the RandomNumSequence function.  ***//
      //*** It will be combined with sequence2 using the Catch() operator only if there is an       ***//
      //*** exception thrown in sequence1 that is caught by the Catch() operator.                   ***//
      //***********************************************************************************************//
      IObservable<int> sequence1 = RandomNumSequence().ToObservable();


      //**************************************************************************************************************************//
      //*** In this catch operation, the exception handler for Observable::Catch will not be executed. This is because         ***//
      //*** sequence1 throws an InvalidOperationException which isn't of the NullReferenceException type specified in the      ***//
      //*** signature of ExNullRefHandler.                                                                                     ***//
      //***                                                                                                                    ***//
      //*** The InvalidOperationException will be caught by the OnError handler instead.                                       ***//
      //**************************************************************************************************************************//
      Console.WriteLine("==============================================================");
      Console.WriteLine("Calling Catch operator with NullReferenceException handler...");
      Console.WriteLine("==============================================================\n");
      sequence1.Catch((Func<NullReferenceException, IObservable<int>>)ExNullRefHandler)
        .Subscribe(i => Console.WriteLine(i),
                  (ex) => Console.WriteLine("\nException {0} in OnError handler\nException.Message : \"{1}\"\n\n", ex.GetType().ToString(), ex.Message));


      //**************************************************************************************************************************//
      //*** In this catch operation, the exception handler will be executed. Because InvalidOperationException thrown by       ***//
      //*** sequence1 is of the InvalidOperationException type specified in the signature of ExInvalidOpHandler().             ***//
      //**************************************************************************************************************************//

        Console.WriteLine("================================================================");
        Console.WriteLine("Calling Catch operator with InvalidOperationException handler...");
        Console.WriteLine("================================================================\n");
        sequence1.Catch((Func<InvalidOperationException, IObservable<int>>)ExInvalidOpHandler)
        .Subscribe(i => Console.WriteLine(i),
                  (ex) => Console.WriteLine("\nException {0} in OnError handler\nException.Message : \"{1}\"\n\n", ex.GetType().ToString(), ex.Message));


      Console.WriteLine("\nPress ENTER to exit...\n");
      Console.ReadLine();
    }




    //*******************************************************************************************************//
    //***                                                                                                 ***//
    //*** This method will yield a random sequence of 5 integers then throw an InvalidOperationException. ***//
    //***                                                                                                 ***//
    //*******************************************************************************************************//
    static IEnumerable<int> RandomNumSequence()
    {
      Random random = new Random();

      //************************************************//
      //*** Yield an a sequence of 5 random integers ***//
      //************************************************//
      for (int i = 0; i < 5; i++)
      {
        yield return random.Next(101);
      }

      //*********************************************************//
      //*** Then throw an InvalidOperationException exception ***//
      //*********************************************************//
      throw new InvalidOperationException("Some Exception Happened!");
    }



    //*********************************************************************************************************//
    //***                                                                                                   ***//
    //*** Simple catch handler for NullReferenceExceptions. This handler looks at the exception message and ***//
    //*** returns a sequence of int.                                                                        ***//
    //***                                                                                                   ***//
    //*********************************************************************************************************//
    static IObservable<int> ExNullRefHandler(NullReferenceException ex)
    {
      //***********************************************************************************************//
      //*** Sequence2 will be part of the resulting sequence if an exception is caught in sequence1 ***//
      //***********************************************************************************************//
      int[] sequence2 = { 0 };

      if (ex.Message == "Some Exception Happened!")
        sequence2 = new int[] { 5001, 5002, 5003, 5004 };

      return sequence2.ToObservable();
    }



    //************************************************************************************************************//
    //***                                                                                                      ***//
    //*** Simple catch handler for InvalidOperationExceptions. This handler looks at the exception message and ***//
    //*** returns a sequence of int.                                                                           ***//
    //***                                                                                                      ***//
    //************************************************************************************************************//
    static IObservable<int> ExInvalidOpHandler(InvalidOperationException ex)
    {
      //***********************************************************************************************//
      //*** Sequence2 will be part of the resulting sequence if an exception is caught in sequence1 ***//
      //***********************************************************************************************//
      int[] sequence2 = { 0 };

      if (ex.Message == "Some Exception Happened!")
        sequence2 = new int[] { 1001, 1002, 1003, 1004 };

      return sequence2.ToObservable();
    }
  }
}

下面是示例代码的示例输出。

==============================================================
Calling Catch operator with NullReferenceException handler...
==============================================================

68
20
17
6
24

Exception System.InvalidOperationException in OnError handler
Exception.Message : "Some Exception Happened!"


================================================================
Calling Catch operator with InvalidOperationException handler...
================================================================

87
29
84
68
23
1001
1002
1003
1004

Press ENTER to exit...

另请参阅

参考

可观测类

捕获重载

System.Reactive.Linq 命名空间