Bundling information into objects (Part 1)

Bundling items

Bundling together related items: tool box.

Images: onairjiw/iStock/Thinkstock

Bundling together related items: assorted chocolates.

Images: Veronika Surovtseva/iStock/Thinkstock

We've used sequences as ways of joining together values of the same type, typically where each value plays a similar role. What about joining together values that play different roles in a computation?

In real-life settings, we bundle together related items in a box. We might collect related but differing tools in a box, with a compartment for each item. There are always food-related examples to be found like the assorted chocolates shown in the figure.

  • Different kinds of boxes exist.
  • Boxes have slots for different items.

We observe that there are different kinds of boxes such as tool boxes and chocolate boxes, and that there are specialized slots for different items.

Grouping related data

We can think of a box-like way of joining related data. A date might consist of the month name as a string and two integers for the day and year, example "October" 10 1896. A point might be defined by its x and y coordinates, for example 8 53. For latitude and longitude, perhaps four values would be stored, for example 43.4667° N, 80.5167° W. For an address, perhaps three, for example "University of Waterloo" "200 University Ave. West" "N2L 3G1" Here's some useful terminology to talk about bundles.

Definition

A class is a type of bundle, such as the class of all points.

An object is an actual bundle, such as the point 8 53.

An attribute is a slot for an item, such as an x-coordinate.

Each type of bundle is called a class. Here we've talked about four different classes. An example of a bundle, with particular values, is called an object. We use the term attribute to refer to one of the slots for an item in a bundle.

Deconstructing dinner

Beef dinner with vegetables, side, starch, and main dish.

Image: Michael Gray/iStock/Thinkstock

Turkey dinner with vegetables, side, starch, and main dish.

Image: Michael Gray/iStock/Thinkstock

Let's illustrate the terms using TV dinners as an example of a class. Here, the TV dinner comes with a choice of beef or turkey, each with its own choice of vegetables, side, starch, and main dish.

Class: dinner

Objects: beef, turkey

Attributes: vegetables, side, starch, main dish

Objects are specific choices of foods to put in the slots, here a beef dinner and a turkey dinner. Each has four slots for the following attributes: vegetables, a side, a starch, and a main dish.


Visualizing objects

Consider another example of an object called lunch, which is of the class “Time”. Assume that the class “Time” has attributes hour, min, and sec. Suppose that the object lunch has attribute values hour = 12, min = 0, and sec = 0.
Object lunch points to a bunch of addresses labelled using the attributes. The addresses associated with the attributes store the value of the attribute.

Class: Time

Objects: lunch

Attributes: hour, min, sec

Values: 12, 0, 0

We can view an object being stored in memory as a bundle of addresses, where the name of the object is stored with the address of the bundle. Just like indices are used to label addresses in sequences, here names of attributes are used to label the addresses in the bundle. The values associated with the attribute addresses are the values of the attributes.

A class as a factory

Another way to view a class is a factory that makes items of a particular variety. There can be individual differences, like in the case of the TV dinners, but only within the limitations of the attributes.

Designing a class

The design principles for a class echo many of the design principles we've been using all along.

Class design recipe

  • Choose meaningful attribute names.
  • Choose attribute types.
  • Record attribute names and types of attributes.

We choose names that convey meaning, and types that fit our needs. Moreover, we ensure that this information is documented, for example, in comments.

Pseudocode for objects

Object lunch points to a bunch of addresses labelled using the attributes. The addresses associated with the attributes store the value of the attribute.

Using as an example the “Time” class seen earlier, we use an assignment statement in which we provide the values for the attributes in order. We use dot notation to refer to a particular attribute of an object, where we use the name of the attribute. lunch ← Time(12, 0, 0)} print(lunch.hour)

For some languages, there may be automatically created functions associated with a class. Such common functions include functions that

  • create objects,
  • determine if an object is in a particular class, or
  • determine if objects are equal.

Bundles inside bundles

The "Event" object swim contains two "Time" objects start and end and a string name. The attribute values of the "Time" object start are hour = 7, min = 30, and sec = 0 and that of end are hour = 8, min = 0, and sec = 0.

There is no restriction on what type of value can be stored in an object.

The figure shows an “Event” object that consists of two “Time” objects and a string. More specifically, the “Event” object called swim contains two “Time” objects called start and end and a string called name. As before, “Time” objects have attributes hour, min, and sec. In this example, the stored values associated with attributes of the object start are hour = 7, min = 30, and sec = 0. The stored values associated with attributes of the object end are hour = 8, min = 0, and sec = 0.

The dot notation swim.start refers to an “Time” object for which we can use swim.start.min to extract the attribute for minutes, with value 30.

Mutation

Since objects are mutable, we can list an attribute on the left side of an assignment statement, resulting in a change to the object.

A "Time" object called lunch with attribute values hour = 12, min = 0, and sec = 0.
Fig. 1
A "Time" object called lunch with attribute values hour = 12, min = 0, and sec = 15.
Fig. 2

For example, consider the object shown in figure 1. Here we have a “Time” object called lunch with attribute values hour = 12, min = 0, and sec = 0. Since objects are mutable, the pseudocode lunch.sec ← 15 changes the value of the attribute sec from 0 to 15, as shown in figure 2.

Aliasing

Consequently, we need to be concerned with aliasing, where an object can be accessed by two different names, and a change under one name changes the value stored under both.

A "Time" object called noon and lunch (the two different names noon and lunch both point to the same "Time" object with attribute values hour = 12, min = 0, and sec = 0.
Fig. 3
A "Time" object called noon and lunch (the two different names noon and lunch both point to the same "Time" object with attribute values hour = 12, min = 0, and sec = 15.
Fig. 4

For exampe, consider again the object shown in figure 1, where we have a “Time” object called lunch with attribute values hour = 12, min = 0, and sec = 0. Then the pseudocode noon ← lunch noon.sec ← 15 creates another name, noon, for the “Time” object, as shown in figure 3, and setting noon.sec ← 15 changes the attribute of sec from 0 to 15 in both lunch and noon, as shown in figure 4.

Methods

Definition

A method is a function associated with a class.

A class contains not only bundles of values, but also functions that can act on those bundles. These use dot notation with the first parameter of the function being followed by a dot and the function name, just as we used for strings. This is no coincidence as in many languages strings are objects.

Advantages of using methods

Why use methods instead of functions?

  • Methods can only be used on the right type of data:
    One advantage is that methods can only be used on data of the correct type, keeping us from making errors.
  • Related functions are grouped together:
    Associating functions with classes also ensures that related functions are grouped together in a logical way