それはある時、唐突に起こりました。

メインスレッドでGUI制御を行い、背景で多数のスレッドが動くアプリケーションの機能拡張&デバッグを行っていました。

そしたら

Invoke(new delegateFullAutoEnd(FullAutoFinished), new object[] { endcode });

上記の行で  例外 FormatException が発生。

FormatExceptionは通常配列の添え字を上限以上に指定してしまった場合に発生する例外なのですが、Invoke周りで発生する要因が思い当たりません。

ちなみにやってる事は、別スレッドで処理を行っている FullAutoスレッドが終了すると イベントを投げて上記のコードを実行、メインスレッドのFullAutoFinished()を返値endcodeを与えて呼び出し、FullAutoスレッドの終了を通知するとゆう物です。

メインスレッドはGUI制御を行っているために、別スレッドから普通にメソッド実行するとエラーになってしまいます。

(別スレッドから呼び出されたpublicメソッドは呼び出しをしたスレッド上で動作するためリソースロック処理を行う必要がある)

そのため、delegateとInvokeを使って間接的にメソッド呼び出しを行い、メインスレッド上でイベント処理を行うとゆう物です。

で、FormatExceptionが発生しそうなのは返値をobjectの配列に格納して渡している部分ですが、これも宣言と異なっていればコンパイル時にエラーになりますし、宣言をチェックしても問題無し・・・

 

取り合えず、初日はお手上げで帰宅。翌日も数時間ああでもないと試行錯誤してたのですが、やはり解決せず。

ここは初心に帰って・・・とメインスレッドから直にFullAutoFinished()をコールしてみようと無理矢理テストコードを書いてみると・・・

問題はFullAutoFinished()の中にありました(汗)

実際にFormatExceptionを出していたのはFullAutoFinished()内の string.Format(”xxxxx”)文でした。

うーん、冗長だから複数行に分割したのが悪かった・・・

string.Format(“A={0} B={1} C={2}”,a,b,c)

みたいに書いてたのを単純に行分割して

string.Format(“A={0}”,a)

string.Format(“B={1}”,b)

string.Format(“C={2}”,c)

って書いちゃってたんですね・・・そりゃアカンわ。

 

Invoke()って、呼び出した先での例外はInvoke()文でThrowされるんですね・・・

まぁ、よく考えるとInvokeってコールバックみたいな動きをするんでこうゆう仕組みになってて当然なんですが、これは知らないと気付かないよなぁ(汗)