人力検索はてな
モバイル版を表示しています。PC版はこちら
i-mobile

【(VB6)配列データの扱いについて】
以下のような流れのコーディングをしました。

流れ1:メソッドAからForm1のSetDataを呼び出し、配列を渡す
流れ2:Form1は受け取った配列をグローバル変数に設定する(イメージは以下の通り)。

Dim Array() As String

Public Sub SetData(BayRef input_Array() As String)
Array = input_Array
End Sub


流れ3:ユーザの操作に応じて配列を修正する。

Private Sub ボタン1クリック()
Array(0)="ボタン1が押されました"
End Sub

Private Sub ボタン2クリック()
Array(0)="ボタン2が押されました"
End Sub


Form1が終了したとき、メソッドAで渡した配列も更新されることを期待したのですが
更新されませんでした。
以下のようにArrayを受け取るためのメソッドを用意したら配列を受け取ることができたのですが、、、、
出来ればForm1で設定したとおりに、メソッドAの配列が自動的に更新されるのが好ましいです
(ポインタのようにデータを直接編集できる方法とあると嬉しいです)。

コーディング方法についてアドバイスいただきたく宜しくお願いします。

Public Sub GetData()As String()
GetData = Array
End Sub



●質問者: harunoharuno
●カテゴリ:コンピュータ
✍キーワード:as String sub vb6 とある
○ 状態 :終了
└ 回答数 : 4/4件

▽最新の回答へ

1 ● ko8820
●50ポイント

標準モジュールに書かないとグローバル変数になりません。

Form内に書くと、スコープがForm内のグローバル変数になります。

http://q.hatena.ne.jp/answer

◎質問者からの返答

『グローバル変数』すいません。言い方間違えました。

確かに標準モジュールに書けば可能な気がしますね。

個人的にはC言語のようにポインタを渡してForm1でポインタが指し示す先を編集するという

のが理想なのですが、そのようなコーディングはできないものでしょうか?


2 ● HALSPECIAL
●50ポイント

この部分で、ディープコピーになってしまっていると思います。

Array = input_Array

呼び出し元のフォームから、配列を取得にいくか、

呼び出し元のフォームにもGetDataメソッドを作ってセットしてあげるかしないとダメだと思います。

◎質問者からの返答

VBコーディングの一般的な記法がわからないので参考になります。

ディープコピーとは、値渡しのことですね(もし違ったら再回答よろしくおねがいしますm(_ _)m)。


3 ● Km1967
●50ポイント

Array = input_Array

これは単に値を渡してるだけだからのぉ。VBでは他の言語のように変数に対して直接、参照とかエイリアスといったような設定を行う事は出来ん。構造体うんぬんの話もでてくるかもしれんが、個別に作成されて統一感の無い多数のフォームを楽して扱いたいといったような向きの相談だろうから多分違うだろう。楽する方法は無いなぁ。


自力で探し出されたようだがMicrosoftのサポートにも載っておるので参照しておいたほうがよかろう。

「Visual Basic では、変数のアドレスを取得する方法」

http://support.microsoft.com/kb/199824/ja


4 ● mj99
●200ポイント ベストアンサー

すでに回答されているとおり、VB6の代入式は「複製」を作ることと同じです。

プロシージャの引数をByValとした場合も「複製」が作られます。


代入式は、単純な型(IntegerやString)だけでなく、ユーザ定義型(Type hoge?End Type)も複製します。

配列変数の場合は、配列のすべての要素が複製されます。


それに対し、

「オブジェクト型変数」は、代入で「複製」が作られず「参照」が作られます。

「参照」を作る場合は、単純に代入するのではなく、

Set A = B

のように、Setキーワードを指定します。


Setキーワードが使えるのは、イコールの両辺が「オブジェクト型」である必要があります

(オブジェクト以外を指定するとコンパイルエラーになる)


----

前置きが長くなりましたが、質問文にあるコードを「オブジェクト型変数=クラスモジュール」を使って書いてみました。

http://www.geocities.co.jp/SiliconValley-Bay/9960/vb/vbclass.htm...


クラスモジュールを一つ追加してください。

オブジェクト名(プロパティシートにある)は、"Class1"とします。

クラスモジュールに書くのはこんだけ

Option Explicit

Public msg As String


以下、フォームモジュールに書く

オブジェクト名は、"Form1"とします。(ちなみに、フォームモジュールはオブジェクト型の一種です)

コマンドボタンCommand1が配置してあるものとします。

Option Explicit

Private localDat As Class1

Public Sub setData(ByVal paramDat As Class1)
 Set localDat = paramDat
End Sub

Private Sub Command1_Click()
 localDat.msg = "押したよ"
End Sub


こんな感じで動作確認します。

Command1のクリックあと、フォームを閉じると、dat.msgが書き換えられるのが確認できると思います。

 Dim dat As New Class1
 Dim frm As New Form1
 
 dat.msg = "押してないよ"
 Call frm.setData(dat)
 frm.Show vbModal
 
 MsgBox dat.msg


----

ここで、

Form1のsetDataメソッドの引数はByValだから、複製が作られるんじゃないのか?

というツッコミがあったりします。

プロシージャの引数がオブジェクト型の場合、

ByValは参照渡しで、

ByRefは参照の参照渡し(C言語で言えば、ポインタのポインタ)

に、なります。

関連質問


●質問をもっと探す●



0.人力検索はてなトップ
8.このページを友達に紹介
9.このページの先頭へ
対応機種一覧
お問い合わせ
ヘルプ/お知らせ
ログイン
無料ユーザー登録
はてなトップ