2011-02-06 6 views
20

C#で例外を無視するより良い方法は、try catchブロック内に置くこととcatchで何もしないことですか?私はこの構文が煩雑であることを知ります。コードブロックの場合、単にそのような方法で「タグ付け」できないので、実行時に無視される例外がわかりますか?C#で例外を無視する

+1

私は無視して例外を知っているが、悪いプログラミングの練習ですが、私の質問はそれではありません。私は空のキャッチブロックを持っていることに意味がないので、質問があります。 –

答えて

23

私は例外を避けるためにトリックがあるとは思わないが、あなたは、次のコードスニペットを使用することができます別の解決策を使用することです

IgnoreExceptions(() => foo()); 

:のようなメソッドを使用して

public void IgnoreExceptions(Action act) 
{ 
    try 
    { 
     act.Invoke(); 
    } 
    catch { } 
} 

に見えますAOP(Aspect Oriented Programming) - PostSharpというツールがあり、特定のアセンブリ/クラス/メソッドのすべての例外を探し出すことができます。これは、探しているものに近いものです。

+8

* @ Dror *、良いアイデア。ただし、コードに微妙なバグがあることに注意してください.CLRでは実際に* Exception型のオブジェクトだけでなく、*任意の*値もスローされます(この制限はC#によってのみ適用されます)。だから、単に 'catch'ブロックを次のように書き直すべきです:**' catch {} '**;それ以外の場合は、通常とは異なる例外が実際に呼び出し側に返される可能性があります。 - たとえば[このブログ記事](http://blogs.msdn.com/b/shawnfa/archive/0001/01/01/400749.aspx)(約2ページ分)を参考にしてください。 – stakx

+0

(私は今修正しました。あなたのコードで別のタイプミスが見つかった時に、修正しました)。 – stakx

+1

act.Invoke()の代わりに、なぜ使用しないのですか行為()? –

1

いいえ例外が発生すると、ブロックはcatchブロックで処理されるか、またはプロセス全体が終了するまで、コールスタックを復帰します。

5

これはAOPで行うことができます。例えば、Postsharpは、そのような属性を適用したメソッドで特定の例外をスキップするような属性を簡単に実装することを可能にします。 AOPがなければ、私はそれをする良い方法は見当たりません(私たちがそういったことをする良い方法があると仮定すれば))。

Postsharpを使用すると、このような方法であなたの方法を飾ることができるようになります:

[IgnoreExceptions(typeof(NullReferenceException), typeof(StackOverflowException))] 
void MyMethod() { ... } 
3

一つの方法は、アスペクト指向プログラミング(AOP)のadvantgeを取ることです。 PostSharpをご覧ください。 Hereは、例外が発生した場合にtry..catchブロックで処理できるように、メソッドで例外属性を使用する例です。

EDIT:

はいああ、ドロールの提案にも良いものです。私はエンタープライズライブラリでその例を見てきました。これは、プロジェクトにサードパーティのフレームワーク(PostSharpなど)を持たせたくない場合は、より効果的です。

2

私はあなたにこれを可能にするメカニズムを知らない。

一般に例外を無視することも非常に悪い習慣と考えられます。正当な理由により例外が発生している(または常にそうでなければならない)。それ以外のものがなければ、少なくともログに記録するべきです。

特定のタイプの例外がアプリケーションにとって重大ではないことが分かっている場合は、Application.UnhandledExceptionイベントを使用してクラッシュすることを防ぎ、そのような例外がないかどうかを確認できます。これは、例外をすべてのスタックフレームから最下部まで伝播することに注意してください。

0

いいえ例外がスローされた場合は、通常、発生したクリティカルエラーです。あなたはそれを無視したくない。

エラーをチェックするためにコードを書き直してください。本当に失敗した場合にのみ例外がキャストされます。

たとえば、オブジェクトが有効な整数かどうかを確認するために、Int32.ParseではなくInt32.TryParseを使用します。例外がキャストされると非常に高価であり、多くのキャストがアプリケーションのパフォーマンスに重大な影響を与えることに注意してください。

+2

Jon skeet quote: "例外があなたのパフォーマンスを大幅に損なうポイントに到達した場合、パフォーマンス以外の例外の使用に関して問題があります。" http://www.yoda.arachsys.com/csharp/exceptions2.html –

0

空のキャッチブロックは、非常に臭いコードです。一言で言えば、それらを書くための簡略な方法を追求すべきではありません。

ルール1は、「処理できない場合はキャッチしない」です。 ルール#1aは、「実際に例外を処理していない場合は、それを再スローします。

アプリをクラッシュさせないようにする場合は、ほとんどの場合、より適切なメカニズムが使用できます。 .NETには、Application、Dispatcher、およびAppDomainレベルのUnhandledExceptionイベント、およびバックグラウンドスレッドで未処理の例外を通知するためのイベントが含まれています。このレベルでは、アプリの状態を確認できない場合は、悪いことをユーザーに通知してアプリを終了することをお勧めします。

+0

例外の処理は例外の処理です。たとえば、ロギングフレームワークでビジネス機能が動作しなくなる例外をスローすることは望ましくありません。基本的には、必須ではない必須のコードに問題がある可能性があるため、主なタスクが失敗することは望ましくありません。ルール1ルールは決まっていないはずです。なぜあなたは何かをし、それがどのような意味を持つのかを理解する必要があります。また、あなたの返信はどのように元の質問に明快さをもたらしますか? – NoOneSpecial

0

以前の回答に基づいて作成した拡張メソッドを提供したかったのです。誰かを助けることを願っています。

/// <summary> 
/// Extension methods for <see cref="Action"/> objects. 
/// </summary> 
public static class ActionExtensions 
{ 
    /// <summary> 
    /// Executes the <paramref name="action"/> and ignores any exceptions. 
    /// </summary> 
    /// <remarks> 
    /// This should be used in very rare cases. 
    /// </remarks> 
    /// <param name="action">The action to execute.</param> 
    public static void IgnoreExceptions(this Action action) 
    { 
     try { action(); } 
     catch { } 
    } 

    /// <summary> 
    /// Extends an existing <see cref="Action"/> so that it will ignore exceptions when executed. 
    /// </summary> 
    /// <param name="action">The action to extend.</param> 
    /// <returns>A new Action that will ignore exceptions when executed.</returns> 
    public static Action AddIgnoreExceptions(this Action action) 
    { 
     return() => action.IgnoreExceptions(); 
    } 
} 

そして、ユニットテスト:

[TestClass] 
public class ActionExtensionsTests 
{ 
    [TestMethod] 
    public void IgnoreException() 
    { 
     Action justThrow =() => { throw new InvalidOperationException(); }; 
     justThrow.IgnoreExceptions(); 
    } 
    [TestMethod] 
    public void AddIgnoreException() 
    { 
     Action justThrow =() => { throw new InvalidOperationException(); }; 
     var newAction = justThrow.AddIgnoreExceptions(); 
     newAction(); 
    } 
} 
0
public static void Ignore<T>(Action a) where T : Exception 
    { 
     try 
     { 
      a(); 
     } 
     catch (T) 
     { 
     } 
    } 

使用するには:

Ignore<InvalidOperationException>(() => foo()); 
関連する問題