A Geologist’s Introduction to Object-Oriented Programming in Python

Using geological data to explain the basics of OOP

Dekha
Python Land
4 min readJun 16, 2021

--

Photo by lucas wesney on Unsplash

What is Object-Oriented Programming?

Object-Oriented Programming (OOP) is a programming paradigm based on the concept of “objects” (Wikipedia). A bunch of objects that are arranged into one group can be called a class. OOP can make the developer focus more on manipulating the object rather than manipulating the logic.

For example, in a showroom, there are various types of vehicles, as follows:

  • One jeep has 4 doors, 4 wheels, and green color
  • One motorcycle has no door, 2 wheels, and white color
  • One minibus has 6 doors, 4 wheels, and red color

If we apply OOP concepts in this example, we can say that we have a vehicle class with 3 objects (jeep, motorcycle, & minibus), and each object has 3 different attributes (door, wheel, & color). But there are enough car analogies in this world already, so in this article, we will apply the OOP concept on geological data.

Creating Objects in a Class

This article will try to create some objects in a class that is a basic rock description, consisting of lithology, age, and depositional environment. For simplification, we only make 2 rock objects:

  • sandstone,
  • and limestone.

To define the rock description, we need to create a function named __init__ with self as the input. The __init__ function can be filled with various attributes, which is a short description of the rock as shown in the following code.

attributes in the code above (lithology, age, & environment) are often referred to as instance variables since these variables are only bound to each instance/object (not bound to the entire objects in a class).

Defining Class Variables

Unlike instance variables, class variables will have an impact on all objects of a particular class, as shown in the code below:

The difference between instance and class variables is that an instance variable is bound to self (particular object). In contrast, a class variable is bound to rock (class of all objects). Since rock.total is a class variable, the value will increase once we create objects of this class, as shown in the code below:

Converting to DataFrame

A Dataframe is a format that is commonly used in every programming case. Sometimes it is necessary to convert a set of objects into one Dataframe. Therefore we need to know how to call variables on an object to store these variables into the same Dataframe as other objects.

To get to a specific instance variable, we simply ask for object.variable format as in the example below:

To see all the variables in an object, we simply do the __dict__ command as in the example below:

From the results above, we need to store all the objects to one list, then convert them into a Dataframe as shown in the following code.

Inheritance

Inheritance is the ability to form a new class which is an extension of an existing class. Inheritance can form a new class while maintaining the existing methods in the previous class.

Below is an example of how to create a new class (geophysics) which is inherited from the old class (rock). This class contains additional geophysical variables such as velocity:

super().__init__ is a command which states that lithology, age, and environment variables come from the superclass. The new variable (velocity) is written outside of the super().__init__ command. After that, we can print all the instance variables as shown below:

It can be seen that sandstone already has a new variable, ‘velocity’:5800.

Defining Behaviour with Methods (Calculating attributes)

A method is a class function that can perform some commands on a particular object of a class. Below is an example of a method for creating instance variables by calculating pre-existing instance variables:

The P-impedance variable is obtained from the velocity variable by specifying a density value. We need to call the object (sandstone) and specify a density value (2.2) as in the example below.

We can also make changes to an instance variable as we like as in the example below.

It should be noted that if we want to convert all objects to a Dataframe, the variables obtained from the inherited class will also be included in the Dataframe as in the following example:

The results above show that those two objects have differences. Sandstone has new variables, namely velocity and p_impedance, while limestone does not have these variables.

Defining Behaviour/Method (Using convert())

What if we have applied inheritance but want to include only the previous variables when converting to Dataframe? We could create a method that only returns the initial dictionary as an object:

As mentioned earlier, the convert(self) method in the class rock: will return only the initial variable (excluding variables derived from inheritance class).

Instead of using r.__dict__ we use r.convert() so that the variables contained in the inheritances class are not converted into a Dataframe.

Final remarks

Besides those examples, many other OOP features can make programming more efficient, such as private attributes, properties, magic methods, etc. Give it a try, and happy coding :)

--

--

Dekha
Python Land

Earth Scientist | Tech Consultant | Mostly tell stories about Earth Science and Data Analytics 🌏📈 | https://www.linkedin.com/in/mordekhai/