tagCANDY CGI VBレスキュー(花ちゃん) の Visual Basic 2010 用 掲示板(VB.NET 掲示板) [ツリー表示へ]   [Home]
一括表示(VB.NET VB2005)
タイトルDLL内の複数クラスで値を参照/格納する方法は?
記事No2044
投稿日: 2005/08/30(Tue) 10:31
投稿者TCZ
[OSのVer]:Windows XP   [VBのVer]:VB.NET 2003 StandardEdition

.net初心者です。
今、DLL内で複数のクラスを定義して使っています。
よくありがちな共通クラスです。

そこでやりたいことがあるのですが、方法が見つからず困っています。
もし知っている方がいましたら教えてくれませんか?

1.APLからクラスAを呼び出したらクラスAで異常発生
2.クラスAの異常ルーチンでクラスBの変数に値を格納
3.APLからクラスBを呼び出し2の値を参照

最初、2の部分をクラスB内に定義したPropertyを使ってsetしたのですが、
3の時にgetしたら値が「0」になってしまいました・・・(T_T)
今、これを解決するのに四苦八苦してます・・・。
時間のある方がいましたら、宜しくお願いします。

[ツリー表示へ]
タイトルRe: DLL内の複数クラスで値を参照/格納する方法は?
記事No2046
投稿日: 2005/08/30(Tue) 10:54
投稿者なおこ(・∀・)
お世話になります。

まず,APLってdllを使うクラス群のこと(例えばForm)をいっていますか?
あと,例外オブジェクトを使う事はできないのですか?

[ツリー表示へ]
タイトルRe^2: DLL内の複数クラスで値を参照/格納する方法は?
記事No2047
投稿日: 2005/08/30(Tue) 11:15
投稿者TCZ
早速の返信、ありがとうございます。

APLは、Windowsアプリケーションのことを指しています。

例外オブジェクトは、使用していないです。
正直、いまいち使いどころが分からなくて・・・・(T_T)

実際に格納しようとしてる値ってのは、「err.Number」です。
他クラスのtry-catchでcatchに入ってから上記をログ出力用クラスの
propertyにsetしました。

Windwosアプリケーションからログ出力用クラスを呼び出しgetしたら
「0」であった、という事なんです。

ログにOSのエラーコードを出力したいため、今の作りをなるべく変更
しない方法を探している所です。

※ ログ出力用クラスとは、最初の質問で言うとクラスBのことです。

[ツリー表示へ]
タイトルRe^3: DLL内の複数クラスで値を参照/格納する方法は?
記事No2048
投稿日: 2005/08/30(Tue) 15:36
投稿者なおこ(・∀・)
お世話になります。

> 例外オブジェクトは、使用していないです。
> 正直、いまいち使いどころが分からなくて・・・・(T_T)

一般的には,こういった場合は例外オブジェクトを使います。
今回の場合,たぶん普通は,Exceptionクラス辺りを継承した独自の例外クラスを
つくって,catchブロックでそれをnewして,
自分で作った例外オブジェクトのプロパティに値(「err.Number」とかですね)をセットして,
それをThrowして,AP側ではさらにそれをcatchして,画面表示…
なんて流れになるでしょう。その方が後々,楽になったりします。

> ログにOSのエラーコードを出力したいため、今の作りをなるべく変更
> しない方法を探している所です。
上記,独自例外オブジェクトでも実現は可能かと思いますが,
変更したくない,とのご意思の用ですので…ちょっと質問させて下さい。

・classは静的クラスではないですよね?
・差し支えない程度で結構ですので,呼び出される側と呼び出し側のソースを見せていただけますか?

[ツリー表示へ]
タイトルRe^4: DLL内の複数クラスで値を参照/格納する方法は?
記事No2049
投稿日: 2005/08/30(Tue) 17:58
投稿者TCZ
お世話になります。

> ・classは静的クラスではないですよね?
DLLをインポートしてるわけではないので動的クラスだと思っています。
アプリケーションと同じ場所にDLLを配置しています。

> ・差し支えない程度で結構ですので,呼び出される側と呼び出し側のソースを見せていただけますか?
少しソースが長くなってしまいますが、いいでしょうか?
(これでも短くした方なんですが・・・)

〜呼び出し元アプリ〜
    Dim ObjFileMove As New ClsFileMove
    Dim ObjLog As New ClsOutLog
    Dim IntRtn As Integer
    IntRtn = ObjFileMove.FMove("移動前ファイル", "移動後ファイル")
    If IntRtn <> 0 Then
        ObjLog.WriteLog("ログファイル","メッセージファイル")
        Exit Sub
    End If

以下、同じDLL内にクラスA、Bを定義しています。
〜クラスA〜
    'ファイル移動メソッド
    Public Function FMove(ByVal StrMoveBefore As String, _
                           ByVal StrMoveAfter As String) As Integer
        Try
            System.IO.File.Move(StrMoveBefore, StrMoveAfter)
            Return 0
        Catch Ex As Exception
            Dim ObjLog As New ClsOutLog
            ObjLog.PropertyTest = Err.Number
            Return 1
        End Try
    End Funticon

〜クラスB〜
    Public PubIntErrNo As Integer

    'Err.Number設定/取得用プロパティ
    Public Property PropertyTest() As Integer
        Get
            Return PubIntErrNo
        End Get
        Set(ByVal IntNumber As Integer)
            PubIntErrNo = IntNumber
        End Set
    End Property

    'ログ出力メソッド
    Public Function WriteLogApp(ByVal strLogFile As String, _
                                ByVal strMsgFile As String)
        '様々な処理を行う
        'クラスAでセットされた"Err.Number"を取得(したい)
        If PropertyTest <> 0 Then
            StrEC = "(Code=" & CStr(PubIntErrNo) & ")"
        Else
            StrEC = ""
        End If
        'ログ出力実行
    End Function

これが、質問した時のコードです。あれから色々試した所、クラスBの
Public変数宣言を「Public Shared」に変更したら取得する事ができ
ました。
例外オブジェクトとは違うやり方なのでこれが正しいのかは、判断が
難しい所です。

[ツリー表示へ]
タイトルRe^5: DLL内の複数クラスで値を参照/格納する方法は?
記事No2050
投稿日: 2005/08/30(Tue) 19:08
投稿者なおこ(・∀・)
お世話になります。

> > ・classは静的クラスではないですよね?
> DLLをインポートしてるわけではないので動的クラスだと思っています。
> アプリケーションと同じ場所にDLLを配置しています。
おお,書き方がまずかったでした。
これはSharedメンバやメソッドをもつクラスですか?
という意味できいていました。

> 少しソースが長くなってしまいますが、いいでしょうか?
> (これでも短くした方なんですが・・・)
ありがとうございます。
んで,見たのですが,
呼び出し元アプリで,
Dim ObjLog As New ClsOutLogとやっていて,
クラスAでも
Catchブロックで
Dim ObjLog As New ClsOutLogとやっているので,
呼び出し元アプリに制御が戻ってきた時に,
クラスAで設定した値が反映されないのは,当然といえば当然です。
呼び出し元アプリと,クラスAのCatchブロックでのObjLogは
変数名や型は同じでも全く別物ですよね。

> Public変数宣言を「Public Shared」に変更したら取得する事ができ
> ました。
Public変数はあんまりよろしくないですよ,と言う事はおいときまして,
Sharedにしたらウマい事いったのは,
Sharedにすると,Sharedという言葉の通り,変数宣言をどこでやろうと
値が共通で保持されます。
なので,思う値がとれたわけですね。

共通部品として使うのであれば,Sheredの方法はマズイっす。

なので,現状のClsOutLogのままやりたいんであれば,
ClsFileMove.FMove等のメソッドに引数として,
ClsOutLogのインスタンスを渡す方法があります。
# でも,あんまりスマートじゃないですよね。

例外クラス化する例として,コードをちょっと修正してみました。
# Catch ObjLog As ClsOutLogExcepionにブレークポイントを張って,ObjLogを見てみてください。
# これが正しいですよ。という意味ではないですので,参考程度にしてくださいね。

Class Test
    Shared Sub Main()
        Try
            Dim ObjFileMove As New ClsFileMove
            ObjFileMove.FMove("移動前ファイル", "移動後ファイル")
        Catch ObjLog As ClsOutLogExcepion
            ObjLog.WriteLog("ログファイル", "メッセージファイル")
        Catch ex As Exception
            Trace.WriteLine(ex.StackTrace)
        End Try
    End Sub
End Class

Public Class ClsFileMove

    'ファイル移動メソッド
    Public Sub FMove(ByVal StrMoveBefore As String, _
                     ByVal StrMoveAfter As String)
        Try
            System.IO.File.Move(StrMoveBefore, StrMoveAfter)
        Catch Ex As Exception
            Dim ObjLog As New ClsOutLogExcepion
            ObjLog.PropertyTest = Err.Number
            Throw ObjLog
        End Try
    End Sub
End Class

Public Class ClsOutLogExcepion
    Inherits Exception

    Private PubIntErrNo As Integer

    'Err.Number設定/取得用プロパティ
    Public Property PropertyTest() As Integer
        Get
            Return PubIntErrNo
        End Get
        Set(ByVal IntNumber As Integer)
            PubIntErrNo = IntNumber
        End Set
    End Property

    'ログ出力メソッド
    Public Function WriteLog(ByVal strLogFile As String, _
        ByVal strMsgFile As String) As String
        '様々な処理を行う
        Dim StrEC As String
        'クラスAでセットされた"Err.Number"を取得(したい)
        If PropertyTest <> 0 Then
            StrEC = "(Code=" & CStr(PubIntErrNo) & ")"
        Else
            StrEC = ""
        End If
        'ログ出力実行
    End Function
End Class

#以下蛇足。
Errオブジェクトでエラーの内容を判断するより,
折角Try〜Catchしてるのですから,
Catchした例外の種類でどんなエラーか判別するのがいいと思いますよ。

例えば,System.IO.File.Moveなんかだと,
DirectoryNotFoundException…これはディレクトリが無い時等に投げられる。
FileNotFoundException…移動元のファイルが無い時に投げられる。
…他,いろいろ

[ツリー表示へ]
タイトルRe^6: DLL内の複数クラスで値を参照/格納する方法は?
記事No2052
投稿日: 2005/08/31(Wed) 13:51
投稿者TCZ
お世話になります。

すいません。返信が遅くなりました。。。(T_T)

> # Catch ObjLog As ClsOutLogExcepionにブレークポイントを張って,ObjLogを見てみてください。
見てみました。色々な情報が覗けました(^-^)v
うまく利用できれば、結構詳細な内容がログに出力できそうですね。
非常に参考になります!!

忙しい中、ご教示して頂きありがとうございます。
これを参考に内部で調整してみたいと思います。
ではでは。。。

[ツリー表示へ]