VB6中对象的分配 [英] Assignment of objects in VB6

查看:187
本文介绍了VB6中对象的分配的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图通过赋值语句在VB6中创建两个相同的对象;像这样...

  Dim myobj1 As Class1 
Dim myobj2 As Class1

设置myobj1 =新Class1
myobj1.myval = 1
设置myobj2 = myobj1

很明显,这不会创建两个对象,而是两个对同一对象的引用,这不是我后面的。有没有办法以这种方式创建第二个对象,或者我必须一次复制一个成员的对象...

 设置myobj2 = new Class1 
myobj2.mem1 = myobj1.mem1
...



编辑2 Scott Whitlock更新了他的优秀答案,代码段。

 私人类型MyMemento 
Value1 As Integer
Value2 As String
结束类型

私人财物作为MyMemento

公共财产让myval(ByVal newval As Integer)
Memento.Value1 = newval
结束资产

公共属性Get myval()As Integer
myval = Memento.Value1
结束属性

友情属性让SetMemento(new_memento As MyMemento)
Memento = new_memento
结束属性

公共函数Copy()As Class1
Dim Result As Class1
Set Result = New Class1
Result.SetMemento = Memento
设置复制=结果
结束函数

然后在代码中执行赋值, / p>

 设定mysecondobj = myfirstobj.Copy 


解决方案

与许多现代语言一样,VB6有值类型和引用类型。类定义引用类型。另一方面,你的基本类型如 Integer 是值类型。



基本的区别在于赋值: / p>

  Dim a as Integer 
Dim b as Integer
a = 2
b = a
a = 1

结果是 a 是1, b 是2.这是因为值类型中的赋值是一个副本。这是因为每个变量都具有为堆栈中的分配的空间(在VB6的情况下,整数在堆栈上占用2个字节)。



对于类,它的工作方式不同:

  Dim a as MyClass 
Dim b as MyClass
设置a =新的MyClass
a.Value1 = 2
设置b = a
a.Value1 = 1

结果是 a.Value1 b.Value1 都是1 。这是因为对象的状态存储在堆中,而不是堆栈上。只有对象的引用存储在堆栈中,因此 Set b = a 将覆盖引用。有趣的是,VB6通过强制您使用 Set 关键字来明确这一点。



现在,您可以创建自己的值类型(在VB6中,它们称为用户定义类型,但在大多数其他语言它们称为结构或结构)。这是教程



类和用户定义类型之间的区别(除了作为引用类型的类和作为值类型的UDT)是一个类可以包含UDT不能的行为(方法和属性)。如果你只是寻找一个记录类型的类,那么UDT可能是你的解决方案。



你可以使用这些技术的混合。假设你需要一个类,因为你有一些行为和计算,你想包括数据。您可以使用纪念模式来保存对象在UDT中的状态:



键入MyMemento
Value1 As Integer
Value2 As String
结束类型

在您的课程中,请确保全部您的内部状态存储在 MyMemento类型的私有成员。写你的属性和方法,所以他们只使用一个私有成员变量中的数据。



现在复制你的对象很简单。只需在你的类上写一个名为 Copy()的新方法,该方法返回你的类的一个新实例,并用它自己的memento的副本初始化:

 私人纪念品MyMemento 

Friend Sub SetMemento(NewMemento As MyMemento)
Memento = NewMemento
End Sub

公共函数Copy()as MyClass
Dim Result as MyClass
Set Result = new MyClass
调用Result.SetMemento(Memento)
设置复制=结果
结束函数

朋友只隐藏它从你的项目之外的东西,所以它不做太多隐藏 SetMemento sub,但它是所有你可以做的VB6。



HTH


I am attempting to create two identical objects in VB6 by assignment statements; something like this...

Dim myobj1 As Class1
Dim myobj2 As Class1

Set myobj1 = New Class1
myobj1.myval = 1
Set myobj2 = myobj1

It has become apparent that this doesn't create two objects but rather two references to the same object, which isn't what I am after. Is there any way to create a second object in this sort of way, or do I have to copy the object one member at a time...

Set myobj2 = new Class1
myobj2.mem1 = myobj1.mem1
...

?

Edit 2 Scott Whitlock has updated his excellent answer and I have incorporated his changes into this now-working code snippet.

Private Type MyMemento
     Value1 As Integer
     Value2 As String
End Type

Private Memento As MyMemento

Public Property Let myval(ByVal newval As Integer)
Memento.Value1 = newval
End Property

Public Property Get myval() As Integer
myval = Memento.Value1
End Property

Friend Property Let SetMemento(new_memento As MyMemento)
    Memento = new_memento
End Property

Public Function Copy() As Class1
     Dim Result As Class1
     Set Result = New Class1
     Result.SetMemento = Memento
     Set Copy = Result
End Function

One then performs the assignment in the code thus...

Set mysecondobj = myfirstobj.Copy

解决方案

Like many modern languages, VB6 has value types and reference types. Classes define reference types. On the other hand, your basic types like Integer are value types.

The basic difference is in assignment:

Dim a as Integer
Dim b as Integer
a = 2
b = a
a = 1

The result is that a is 1 and b is 2. That's because assignment in value types makes a copy. That's because each variable has space allocated for the value on the stack (in the case of VB6, an Integer takes up 2 bytes on the stack).

For classes, it works differently:

Dim a as MyClass
Dim b as MyClass
Set a = New MyClass
a.Value1 = 2
Set b = a
a.Value1 = 1

The result is that both a.Value1 and b.Value1 are 1. That's because the state of the object is stored in the heap, not on the stack. Only the reference to the object is stored on the stack, so Set b = a overwrites the reference. Interestingly, VB6 is explicit about this by forcing you to use the Set keyword. Most other modern languages don't require this.

Now, you can create your own value types (in VB6 they're called User Defined Types, but in most other languages they're called structs or structures). Here's a tutorial.

The differences between a class and a user defined type (aside from a class being a reference type and a UDT being a value type) is that a class can contain behaviors (methods and properties) where a UDT cannot. If you're just looking for a record-type class, then a UDT may be your solution.

You can use a mix of these techniques. Let's say you need a Class because you have certain behaviors and calculations that you want to include along with the data. You can use the memento pattern to hold the state of an object inside of a UDT:

Type MyMemento
    Value1 As Integer
    Value2 As String
End Type

In your class, make sure that all your internal state is stored inside a private member of type MyMemento. Write your properties and methods so they only use data in that one private member variable.

Now making a copy of your object is simple. Just write a new method on your class called Copy() that returns a new instance of your class and initialize it with a copy of its own memento:

Private Memento As MyMemento

Friend Sub SetMemento(NewMemento As MyMemento)
    Memento = NewMemento
End Sub

Public Function Copy() as MyClass
    Dim Result as MyClass
    Set Result = new MyClass
    Call Result.SetMemento(Memento)
    Set Copy = Result
End Function

The Friend only hides it from stuff outside your project, so it doesn't do much to hide the SetMemento sub, but it's all you can do with VB6.

HTH

这篇关于VB6中对象的分配的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆