In VB.NET, there is a fundamental distinction between value types and reference types. Value types have storage allocated immediately on the stack when the variable is declared. Reference types have storage allocated on the heap when they are instantiated , not when they are just declared, and the variable is only a reference to the actual object containing the data. We have been looking at classes in some detail. A class defines a reference type. In this section we survey the entire VB.NET type system, including simple types such as Integer and Decimal . In VB.NET, a Structure has many similarities to a Class , but it is a value type. This means that assigning from one structure variable to another causes the entire structure to be copied, rather than just a reference being copied . Another important kind of value type in VB.NET is an Enum , which defines a related set of constants (i.e., an enumeration). We will examine several other important types, including string, array, interface, and delegate. We will discuss the default values that get assigned to variables when there is not an explicit initialization. We will see that all types in VB.NET are rooted in a fundamental base class called Object . In VB.NET, "everything is an object," and value types are transparently converted to object references as needed through a process known as boxing . The inverse process, unboxing , returns an object to the value type from which it came. Overview of Types in VB.NET In VB.NET there are two kinds of types: -
Value types -
Reference types Value Types Value types directly contain their data. Each variable of a value type has its own copy of the data. Value types typically are allocated on the stack and are automatically destroyed when the variable goes out of scope. Value types include the simple types like Integer and Decimal , as well as structures, and enumeration types. Reference Types Reference types do not contain data directly but only refer to data. Variables of reference types store references to data, called objects. Two different variables can reference the same object. Reference types are allocated on the managed heap and eventually get destroyed through a process known as garbage collection . Reference types include class types, array types, interfaces, and delegates. Value Types In this section we survey all the value types, including the simple types, structures, and enumerations. Simple Types The simple data types (also known as the primitive data types) are general-purpose value data types, including numeric, character, boolean, and date types. -
The SByte data type is an 8-bit signed integer. -
The Byte data type is an 8-bit unsigned integer. -
The Short data type is a 16-bit signed integer. -
The Integer data type is a 32-bit signed integer. -
The Long data type is a 64-bit signed integer. -
The Char data type is a Unicode character (16 bits). -
The Single data type is a single-precision floating point. -
The Double data type is a double-precision floating point. -
The Decimal data type is a decimal type with 28 significant digits (typically used for financial calculations). -
The Boolean data type is a Boolean ( true or false ). -
The Date data type is a represents a date and time. Types in System Namespace There is an exact correspondence between the simple VB.NET types and types in the System namespace. VB.NET reserved words are simply aliases for the corresponding types in the System namespace. Table 3-3 shows this correspondence. Table 3-3. Types in VB.NET and the System Namespace VB.NET Reserved Word | Type in System Namespace | SByte | System.SByte | Byte | System.Byte | Short | System.Int16 | Integer | System.Int32 | Long | System.Int64 | Char | System.Char | Single | System.Single | Double | System.Double | Decimal | System.Decimal | Boolean | System.Boolean | Date | System.DateTime | Structures A Structure is a value type, which can group heterogeneous types together. It can also have methods . The key difference between a class and a structure is that a class is a reference type and a structure a value type. A class must be instantiated explicitly using New . The new instance is created on the heap, and memory is managed by the system through a garbage-collection process. A new instance of a structure is created on the stack, and the instance will be deallocated when it goes out of scope. There are different semantics for assignment, whether done explicitly or via call by value mechanism in a method call. For a class, you will get a second object reference, and both object references refer to the same data. For a structure, you will get a completely independent copy of the data in the structure. A structure is a convenient data structure to use for moving data across a process or machine boundary, and we will use structures in our case study. For example, we will use a struct to represent customer data Public Structure CustomerListItem Public CustomerId As Integer Public FirstName As String Public LastName As String Public EmailAddress As String End Structure Enumeration Types Another kind of value type is an enumeration type. An enumeration type is a distinct type with named constants. Every enumeration type has an underlying type, which is one of the following. An enumeration type is defined through an Enum declaration. Public Enum BookingStatus As Byte HotelNotFound ' 0 implicitly RoomsNotAvailable ' 1 implicitly Ok = 5 ' explicit value End Enum If the type is not specified, Integer is used. By default, the first Enum member is assigned the value 0, the second member 1, and so on. Constant values can be explicitly assigned. You can make use of an enumeration type by declaring a variable of the type indicated in the Enum declaration (e.g., BookingStatus ). You can refer to the enumerated values by using the dot notation. Here is some illustrative code: ... Dim status As BookingStatus status = hotel.ReserveRoom(name, dateTime) If status = BookingStatus.HotelNotFound Then Console.WriteLine("Hotel not found") End If ... Reference Types A variable of a reference type does not directly contain its data but instead provides a reference to the data stored in the heap. In VB.NET, there are the following kinds of reference types: Reference types can have the special value Nothing , which indicates the absence of an instance. VB.NET uses the Nothing keyword for this purpose, rather than the VB 6.0 keywords Empty and Null , which are no longer supported. We have already examined classes in some detail, and we will look at arrays in Chapter 4. Interfaces and delegates will be covered in Chapter 6. Class Types A class type defines a data type that can have fields, methods, constants, and other kinds of members . Class types support inheritance . Through inheritance a derived class can extend or specialize a base class. We will discuss inheritance in Chapter 5. Two classes in the .NET Framework class library are particularly important: Object and String . Object The Object class type is the ultimate base type for all types in all .NET languages. Every VB.NET reference type derives directly or indirectly from Object . The fully qualified name is System.Object . It has methods such as ToString , Equals , and Finalize , which we will study later. String The String class encapsulates a Unicode character string. The string type is a NotInheritable class. (A NotInheritable class is one that cannot be used as the base class for any other classes.) The String class inherits directly from the root Object class. String literals are defined using double quotes. There are useful built-in methods for String . For now, note that the Equals method can be used to test for equality of strings. Dim a As String = "hello" If a.Equals("hello") Then Console.WriteLine("equal") Else Console.WriteLine("not equal") End If There are also overloaded [5] operators for comparing strings: [5] An operator is overloaded if it applies to different kinds of data types. The = operator is used for numerical data types and also for the String data type. If a = "hello" Then ... We will study String in detail later in Chapter 4. Default Values Several kinds of variables are automatically initialized to default values: The default value of a variable of reference type is Nothing . For simple types (primitive value types) the default field values correspond to a bit pattern of all zeros: -
For Integer types, the default value is 0. -
For Char , the default value is the Unicode value zero. -
For Single , the default value is 0.0F. -
For Double , the default value is 0.0R. -
For Decimal , the default value is 0.0D. -
For Boolean , the default value is False . For an Enum type, the default value is 0. For a Structure type, the default value is obtained by setting all value type fields to their default values, as described above, and all reference type fields to Nothing . Boxing and Unboxing One of the strong features of .NET is that is has a unified type system. Every type, including the simple built-in types such as Integer , derives from System.Object . In .NET, "everything is an object." A language such as Smalltalk also has such a feature but pays the price of inefficiency for simple types. Languages such as C++ and Java treat simple built-in types differently from objects, thus obtaining efficiency but at the cost of a non-unified type system. .NET languages, such as VB.NET, enjoy the best of both worlds through a process known as boxing . Boxing converts a value type such as Integer or a Structure to an object reference and this is done implicitly and automatically. Unboxing converts a boxed value type (stored on the heap) back to an unboxed simple value (stored on the stack). Unboxing is done through a type conversion known as a type cast. Specific type casts can be accomplished using the CObj , CByte , CShort , CInt , CLng , CSng , CDbl , CDec , CChar , CBool , CDate , and CStr keywords. In addition, AscW and ChrW can be used to convert between Char and Integer types. You can also use the general casting keyword CType to convert to an arbitrary type. Dim x As Integer = 5 Dim o As Object = x ' boxing x = CType(o, Integer) ' unboxing |