SQL — Substring with Negative Indexing | by Deepak Khandelwal | Towards Data Science

In this post, I have discussed about one of the very important string related operations in SQL — SUBSTR with the application of negative indexing.
SUBSTR is used to extract the certain part of the given string from a given position. I have used SQLite-implementation of SUBSTR to illustrate the use of negative indexing.
I have used movielens database to write the various queries of SUBSTR. This database has the four tables — links, movies, ratings, tags. We are interested in movies table. The first 20 rows of the table are as follows
Now we will go through the details of SUBSTR operator and it parameters.SUBSTR accepts three parameters as shown in Table 1. The last parameter — Z, is optional.
Both Y and Z parameters can take positive and negative index values. Furthermore, Z is optional, Therefore we have the following six possibilities
╔══════════╦══════════╗║    Y     ║    Z     ║╠══════════╬══════════╣║ Positive ║    -     ║║ Negative ║    -     ║║ Positive ║ Positive ║║ Positive ║ Negative ║║ Negative ║ Positive ║║ Negative ║ Negative ║╚══════════╩══════════╝
Now we will write queries for each of the six aforementioned possibilities. Before that, we should know how negative indexing works in SUBSTR. The positive indexing starts from number 1 which will be the leftmost character and the negative indexing starts from number -1 which will be the rightmost character in the string as shown in figure 3.
The following table contains the details of how the six combinations of Y and Z are evaluated.
Now we will perform some queries where we can use to get the desired result.
Query 1: Write a query to remove movie release year from movie title and display only titles.
SELECT TRIM(SUBSTR(TRIM(title), -6, (SELECT 6-MAX(LENGTH(title))                                     FROM movies)))FROM movies
In the query 1, we have the following values for X, Y, Z1. X = TRIM(title) We have trimmed the title column of the movie table to eliminate any possibility of having spaces at both the ends of movie title.2. Y = -6Why -6? Because we have the following structure for all the movie titles —<title><space>(<four digit movie release year>). We have last 6 characters as ‘(‘, ‘<digit>’, ‘<digit>’, ‘<digit>’, ‘<digit>’, ‘)’ .
3. Z = (SELECT 6-MAX(LENGTH(title)) FROM movies) Since the titles’s lengths vary and we have to make sure that each of the title should appear in the result in its entirety. We have handled the case having maximum title length, it will work for the rest of cases. We can break down this operation into the following steps — First, lengths of all the movie titles are calculated — LENGTH(title). It results in a table containing the length of each and every movie title.Second, maximum length is calculated — MAX(LENGTH(title)) . It results in maximum length of title which is 158.Third, 6-MAX(LENGTH(title)) results in 6–158 = -152.Hence we have Z as -152. Here, both Y and Z have negative values. It starts reading from -6th character which is ‘(’, then it reads, absolute value of -152 which is 152, characters preceding ‘(’ excluding ‘(’ character. Since 152 is the maximum length a title can have in the movie table, it will extract titles for all the movies. For example, ‘Jimmy Hollywood (1994)’ will result in ‘Jimmy Hollywood ’ and after trimming ‘Jimmy Hollywood’ .
Query 2: Write a query to remove title from movie title and display only year.
Similarly, We can extract the movie release year from the title column.
SELECT TRIM(SUBSTR(TRIM(title), -5, 4))FROM movies
In this query, Extraction of movie release year starts from -5th character which is first digit of movie release year, then 4 characters following that are fetched including the -5th character.
Now we can leverage the power of negative indexing to perform some specific operations. For example — we can group by the result of query 2 on movie release year and can get the count of movies released in each year.
Query 3: Write a query to find out the release years of the movie Mission Impossible.
SELECT TRIM(SUBSTR(TRIM(title), -5, 4))FROM moviesWHERE title LIKE "Mission: Impossible%"
At last, one point I want to highlight is that the above operations could be performed using regular expressions in much more elegant and efficient way, but in this article, I have tried to show application of negative indexing in SUBSTR.