2

Phoneオブジェクトを含むクラスがあります。

電話は仮想電話であり、クラスのコンストラクターで、接続する仮想電話のIPアドレスとポートを渡します。

次に、コンストラクター内で、 Connectというメソッドを実行します。Connectメソッドでは、電話のIPアドレス/ポートコンボからIPEndPointオブジェクトをインスタンス化し、次にSocketオブジェクトをインスタンス化し、SocketオブジェクトConnectメソッドを実行して、 IPEndPointをパラメーターとして渡します。

電話サーバーが特定の電話(私の仕事ではない)に対して適切に構成されていない場合、接続は拒否され、SocketExceptionがスローされます。私はこの例外をキャッチしようとしています。

これはWindowsフォームアプリケーションです。Formオブジェクトのスコープ内ですが、コンストラクター/メソッドのスコープ外では、次のようにインスタンス化されていないプライベートフィールドとして電話があります(IPhoneは電話が使用するインターフェイスです)。

private IPhone _phone;

SetupPhoneというメソッドがあり、ここで電話オブジェクトをインスタンス化し、ここで例外をキャッチしようとしています。

private void SetupPhone()
{
    try
    {
        _phone = new Phone(AgentDetails.IPAddress, AgentDetails.Port);
    }
    catch(SocketException ex)
    {
        Log.LogException("Error mapping phone to port", ex);
        ShowBaloonTip("An error occured starting CTI. Please select your name from the list to try again", ToolTipIcon.Error);

        ChangeUser();
        return;
    }

    //Subscribe to Phone events here
}

電話オブジェクトのコンストラクターは次のとおりです。

public Phone(string ipAddress, int port, string password = "FooBar")
{
    Connect(ipAddress, port, password);
}

Connectメソッドは次のとおりです。

public void Connect(string ipAddress, int port, string password)
{
    _phone = new IPEndPoint(IPAddress.Parse(ipAddress), port);
    _socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.IP);

    _socket.Connect(_phone);

    //Redacted
}

適切に設定されていない電話では、次のようにSocketExceptionがスローされます。

例外

オブジェクトコンストラクターで実行されるメソッドによってスローされた例外は、そのオブジェクトのインスタンス化の周りに配置されたtry / catchブロックによって安全にキャッチされるべきだと考えるのは正しくありませんか?それともそうではありませんか?オブジェクトをインスタンス化するときに発生する可能性のあるエラーをキャッチしたいのですが、これは不可能ですか?

4

1 に答える 1

3

http://www.blackwasp.co.uk/VSBreakOnException.aspx

Visual Studioのデバッガーを使用してデバッグモードでプログラムを実行し、例外が発生した場合、デフォルトの動作では、エラーがtry / catchブロックで処理されない限り、実行が一時停止されます。この動作は、例外タイプごとに変更できます。

デバッグモードの例外

ソフトウェアをデバッグモードで実行すると、例外がtry / catch / finallyブロック内で処理されるか、処理されないかによって、スローされた例外に対するVisualStudioの反応が異なります。デフォルト構成を使用する場合、未処理の例外によりプログラムが停止し、例外の詳細が表示されます。処理された例外によってプログラムが停止することはありません。これは、デバッグモードで次のコードを実行することで確認できます。除算が試行されるとDivideByZeroExceptionがスローされますが、プログラムは続行されます。try and catchをコメントアウトすると、例外によって実行が停止します。

try
{
    int i = 0;
    int j = 1;
    Console.WriteLine(j / i);
}
catch
{
    Console.WriteLine("Caught an exception");
}
Console.ReadLine();

この動作は、ほとんどの状況で役立ちます。ただし、未処理の場合でも特定の種類の例外を無視したり、通常は無視される処理済みの例外を中断したりする場合があります。これは、[例外]ダイアログボックスを使用して制御できます。このダイアログボックスは、[デバッグ]メニューから[例外]を選択するか、Ctrl-Alt-Eを押すことで表示できます。

ダイアログボックスのメイン領域には、ツリー構造の例外タイプのリストが表示されます。ツリーのブランチを展開して、例外のさまざまなグループと各カテゴリ内の個々のタイプを表示できます。例外とグループごとに2つのチェックボックスが表示されます。[スロー]チェックボックスがオンになっている場合、選択された例外、または選択された例外グループの1つに遭遇すると、プログラムは中断します。これには、処理された例外が含まれます。「ユーザー未処理」チェックボックスがチェックされている場合、プログラムは例外が未処理の場合にのみ中断します。オプションを試すには、ツリー構造でDivideByZeroExceptionタイプを見つけます。例外をすばやく見つけるには、[検索]ボタンをクリックして、検索するアイテムの名前の一部を入力します。最初に一致するアイテムが見つかります。これが目的の例外でない場合は、[次を検索]ボタンをクリックして、一致を循環します。DivideByZeroExceptionを見つけたら、適切な「スロー」オプションをチェックします。サンプルプログラムを実行すると、処理された例外でプログラムが停止することがわかります。

すべてリセット

[例外]ダイアログボックスには、注目に値するいくつかのオプションがあります。これらの最初のものは、[すべてリセット]ボタンです。アプリケーションのデバッグに役立つようにダイアログボックスのオプションを変更した場合は、このボタンをクリックして、すべてのオプションを元の設定にリセットできます。

カスタム例外の構成

Exceptionクラスまたはそのサブクラスの1つから機能を継承する独自の例外タイプを定義した場合は、ダイアログボックスを使用して構成することをお勧めします。標準の例外タイプではないため、デフォルトではリストに表示されません。ただし、[追加]ボタンをクリックして詳細を入力することで追加できます。.NET例外の場合は、ドロップダウンリストから[共通言語ランタイム例外]オプションを選択していることを確認する必要があります。次に、例外クラスの完全修飾名を指定する必要があります。たとえば、「MyNamespace.MyException」です。

于 2012-11-11T11:47:28.897 に答える