Home

Built-In Classes: The Object Class

 

Fundamentals

 

Introduction

The .NET Framework is a huge library of various classes. Those classes were created in various namespaces and are available from the corresponding libraries. The classs are organized in a hierachical manner so that many cna inherit common behaviors from their ancestry.

The most fundamental class is called Object. Most classes in the .NET Framework directly or indirectly derive from it. Also, when you create a class in your F#, it automatically derives from Object. This meakes sure that all classes share some basic behaviors and characteristics that most or all classes need. Still, you are allowed to overrided any of thoses characteristics in your own classes.

The Object class is defined in the System namespace. As a consequence, when you create an application, as long as you include that namespace in your code file, that class is automatically available.

Equality of Two Class Variables

When you declare and initialize two variables, one of the operations you may want to subsequently perform is to compare their value. To support this operation, the Object class provides its children with a method called Equals. The Equals() method comes in two versions. The first has the following syntax:

abstract Equals : 
        obj:Object -> bool  
override Equals : 
        obj:Object -> bool

This version allows you to call the Equals() method on a declared variable and pass the other variable as argument. This version of the Object.Equals() method is abstract. This allows you to override it in your own class. Here are examples:

open System
open System.Windows.Forms

type StoreItem(number, make, category, subcategory, name, size, price, discrate) =
    let mutable nbr = number
    let mutable mk = make
    let mutable cat = category
    let mutable sub = subcategory
    let mutable nm = name
    let mutable sz = size
    let mutable prc = price
    let mutable rate = discrate

    member this.ItemNumber     with get() = nbr  and set(value) = nbr  <- value
    member this.Manufacturer   with get() = mk   and set(value) = mk   <- value
    member this.Category       with get() = cat  and set(value) = cat  <- value
    member this.SubCategory    with get() = sub  and set(value) = sub  <- value
    member this.ItemName       with get() = nm   and set(value) = nm   <- value
    member this.ItemSize       with get() = sz   and set(value) = sz   <- value
    member this.UnitPrice      with get() = prc  and set(value) = prc  <- value
    member this.DiscountRate   with get() = rate and set(value) = rate <- value
    member this.DiscountAmount with get() = this.UnitPrice * this.DiscountRate / 100.00
    member this.MarkedPrice    with get() = this.UnitPrice - this.DiscountAmount
    new() = StoreItem("", "", "", "", "", "", 0.00, 0.00)
    new(number, make, category, subcategory, name, size, price) = StoreItem(number, make, category, subcategory, name, size, price, 0.00)

    override this.Equals(obj) =
            match obj with
            | :? StoreItem as si -> this.ItemName = si.ItemName
            | _ -> false

let si1 = new StoreItem("279403", "Reef", "Men", "Sandals", "Men's Phantom Ultimate Flip Flop", "10", 45.50, float 0)
let si2 = new StoreItem("927497", "Guess", "Women", "Dresses", "Zip Front Fit and Flare Dressr", "4", 155.75, float 25)
let si3 = new StoreItem("293041", "Anne Klein", "Women", "Skirts", "A-Line Skirt with Lining", "6", 82.50, float 50)
let si4 = new StoreItem("537946", "Guess", "Women", "Dresses", "Zip Front Fit and Flare Dressr", "4", 155.75, float 25)

let equality1 = sprintf "%A" (si1.Equals(si2))
let equality2 = sprintf "%A" (si1.Equals(si3))
let equality3 = sprintf "%A" (si2 = si4)

// Form: Department Store
let departmentStore = new Form()
departmentStore.Width  <- 520
departmentStore.Height <- 225
departmentStore.Text   <- "Department Store"

// Label: Equality 1
let lblEquality1 = new Label()
lblEquality1.Left   <- 12
lblEquality1.Top    <- 18
lblEquality1.Width  <- 500
lblEquality1.Text   <- "Equality of Item 927497 With Item 279403 produces: " + equality1.ToString()
departmentStore.Controls.Add lblEquality1

// Label: Equality 2
let lblEquality2 = new Label()
lblEquality2.Left  <-  12
lblEquality2.Top   <- 42
lblEquality2.Width <- 500
lblEquality2.Text  <- "Equality of Item 927497 With Item 537946 produces: " + equality2.ToString()
departmentStore.Controls.Add lblEquality2

// Label: Equality 3
let lblEquality3 = new Label()
lblEquality3.Left   <- 12
lblEquality3.Top    <- 64
lblEquality3.Width  <- 500
lblEquality3.Text   <- "Equality of Item 279403 With Item 293041 produces: " + equality3.ToString()
departmentStore.Controls.Add lblEquality3

do Application.Run departmentStore

This would produce:

Equality of Two Class Variables

     
 

Stringing an Object

We already know that, to convert the value of a variable declared from a primitive type to a string, you can call the string() or the sprintf() function. To support this operation and make it available to all objects, the Object class is equipped with a method named ToString. Its signature is:

abstract ToString : unit -> string  
override ToString : unit -> string

The default implementation tries to convert any value to a string. In reality, if you create your own class and you want its objects to be converted to a string, you should (must) override this method. Here is an example:

open System
open System.Windows.Forms

type StoreItem(number, make, category, subcategory, name, size, price, discrate) =
    let mutable nbr = number
    let mutable mk = make
    let mutable cat = category
    let mutable sub = subcategory
    let mutable nm = name
    let mutable sz = size
    let mutable prc = price
    let mutable rate = discrate

    member this.ItemNumber     with get() = nbr  and set(value) = nbr  <- value
    member this.Manufacturer   with get() = mk   and set(value) = mk   <- value
    member this.Category       with get() = cat  and set(value) = cat  <- value
    member this.SubCategory    with get() = sub  and set(value) = sub  <- value
    member this.ItemName       with get() = nm   and set(value) = nm   <- value
    member this.ItemSize       with get() = sz   and set(value) = sz   <- value
    member this.UnitPrice      with get() = prc  and set(value) = prc  <- value
    member this.DiscountRate   with get() = rate and set(value) = rate <- value
    member this.DiscountAmount with get() = this.UnitPrice * this.DiscountRate / 100.00
    member this.MarkedPrice    with get() = this.UnitPrice - this.DiscountAmount
    new() = StoreItem("", "", "", "", "", "", 0.00, 0.00)
    new(number, make, category, subcategory, name, size, price) = StoreItem(number, make, category, subcategory, name, size, price, 0.00)

    override this.Equals(obj) =
            match obj with
            | :? StoreItem as si -> this.ItemName = si.ItemName
            | _ -> false

    override this.ToString() =
        "Item #: " + this.ItemNumber + ", " + this.Manufacturer + ", " + this.Category + " " + this.SubCategory + ", Named " + this.ItemName + "(" + this.ItemSize + "), Price: " + string this.UnitPrice

let si1 = new StoreItem("279403", "Reef", "Men", "Sandals", "Men's Phantom Ultimate Flip Flop", "10", 45.50, float 0)
let si2 = new StoreItem("927497", "Guess", "Women", "Dresses", "Zip Front Fit and Flare Dressr", "4", 155.75, float 25)
let si3 = new StoreItem("293041", "Anne Klein", "Women", "Skirts", "A-Line Skirt with Lining", "6", 82.50, float 50)
let si4 = new StoreItem("537946", "Guess", "Women", "Dresses", "Zip Front Fit and Flare Dressr", "4", 155.75, float 25)

let equality1 = sprintf "%A" (si1 = si2)
let equality2 = sprintf "%A" (si1.Equals(si3))
let equality3 = sprintf "%A" (si2 = si4)

// Form: Department Store
let departmentStore = new Form()
departmentStore.Width  <- 520
departmentStore.Height <- 225
departmentStore.Text   <- "Department Store"

// Label: Item 1
let lblItem1 = new Label()
lblItem1.Left   <- 12
lblItem1.Top    <- 18
lblItem1.Width  <- 500
lblItem1.Text   <- si1.ToString()
departmentStore.Controls.Add lblItem1

// Label: Item 3
let lblItem2 = new Label()
lblItem2.Left   <- 12
lblItem2.Top    <- 42
lblItem2.Width  <- 500
lblItem2.Text   <- si2.ToString()
departmentStore.Controls.Add lblItem2

// Label: Item 3
let lblItem3 = new Label()
lblItem3.Left   <- 12
lblItem3.Top    <- 64
lblItem3.Width  <- 500
lblItem3.Text   <- si3.ToString()
departmentStore.Controls.Add lblItem3

// Label: Item 4
let lblItem4 = new Label()
lblItem4.Left   <- 12
lblItem4.Top    <- 88
lblItem4.Width  <- 500
lblItem4.Text   <- si4.ToString()
departmentStore.Controls.Add lblItem4

// Label: Equality 1
let lblEquality1 = new Label()
lblEquality1.Left   <- 12
lblEquality1.Top    <- 118
lblEquality1.Width  <- 500
lblEquality1.Text   <- "Equality of Item 927497 With Item 279403 produces: " + equality1.ToString()
departmentStore.Controls.Add lblEquality1

// Label: Equality 2
let lblEquality2 = new Label()
lblEquality2.Left  <-  12
lblEquality2.Top   <- 142
lblEquality2.Width <- 500
lblEquality2.Text  <- "Equality of Item 927497 With Item 537946 produces: " + equality2.ToString()
departmentStore.Controls.Add lblEquality2

// Label: Equality 3
let lblEquality3 = new Label()
lblEquality3.Left   <- 12
lblEquality3.Top    <- 168
lblEquality3.Width  <- 500
lblEquality3.Text   <- "Equality of Item 279403 With Item 293041 produces: " + equality3.ToString()
departmentStore.Controls.Add lblEquality3

do Application.Run departmentStore

This would produce:

Stringing an Object

Hashing an Object

Hashing an object consists of providing it with a number that can be used when the class is involved in a collection. To support this, the Object class is equipped with the GetHashCode() method. Its signature is:

abstract GetHashCode : unit -> int  
override GetHashCode : unit -> int

Normally, when you override the ToString() method, it is also suggested that you override this method. Here is an example:

open System
open System.Windows.Forms

type StoreItem(number, make, category, subcategory, name, size, price, discrate) =
    let mutable nbr = number
    let mutable mk = make
    let mutable cat = category
    let mutable sub = subcategory
    let mutable nm = name
    let mutable sz = size
    let mutable prc = price
    let mutable rate = discrate

    member this.ItemNumber     with get() = nbr  and set(value) = nbr  <- value
    member this.Manufacturer   with get() = mk   and set(value) = mk   <- value
    member this.Category       with get() = cat  and set(value) = cat  <- value
    member this.SubCategory    with get() = sub  and set(value) = sub  <- value
    member this.ItemName       with get() = nm   and set(value) = nm   <- value
    member this.ItemSize       with get() = sz   and set(value) = sz   <- value
    member this.UnitPrice      with get() = prc  and set(value) = prc  <- value
    member this.DiscountRate   with get() = rate and set(value) = rate <- value
    member this.DiscountAmount with get() = this.UnitPrice * this.DiscountRate / 100.00
    member this.MarkedPrice    with get() = this.UnitPrice - this.DiscountAmount
    new() = StoreItem("", "", "", "", "", "", 0.00, 0.00)
    new(number, make, category, subcategory, name, size, price) = StoreItem(number, make, category, subcategory, name, size, price, 0.00)

    override this.Equals obj =
            match obj with
            | :? StoreItem as si -> this.ItemName = si.ItemName
            | _ -> false

    override this.ToString() =
        "Item #: " + this.ItemNumber + ", " + this.Manufacturer + ", " + this.Category + " " + this.SubCategory + ", Named " + this.ItemName + "(" + this.ItemSize + "), Price: " + string this.UnitPrice

    override this.GetHashCode() =
        this.GetHashCode()

Finalizing a Variable

When you create an object and while you are using it, it occupies the computer mememory and uses resources. When the object is not used anymore, it should be removed from memory and the resources it was using should be released. To assist you with performing these operations on your objects, the Object class is equipped with a method named Finalize. Its signature is:

abstract Finalize : unit -> unit  
override Finalize : unit -> unit

In most cases, you will never need to call this method because the compiler takes care of memory cleaning for you. In rare cases, you can override this method in your classes.

   
   
 

Home Copyright © 2015 FunctionX Home