How to split a string into array in Bash

Aug 04, 2023#bash

Whether you are processing input data, parsing configuration files, or handling command-line arguments, the ability to split strings into arrays is a fundamental skill that greatly enhances the versatility and functionality of your Bash scripts.

A string may contain multiple elements separated by specific characters like commas, colons, or spaces. By splitting the string into an array, you can access and process individual elements separately, enabling more flexible data handling, such as filtering, modifying, or performing calculations.

There are several methods to achieve this in Bash, each with its strengths and use cases.

Using IFS variable and read command

The most common approach is to use the IFS (Internal Field Separator) variable to specify the delimiter character and then use read or parameter expansion to split the string.

#!/bin/bash

# Input string
my_string="apple,banana,orange"

# Set the delimiter using IFS (comma in this case)
IFS="," read -ra my_array <<< "$my_string"

# Print each element of the array
for element in "${my_array[@]}"; do
  echo "$element"
done

In Bash, the IFS is a special environment variable that determines how the shell interprets word splitting, which is the process of breaking a string into individual words or fields. The IFS variable contains a set of characters that act as delimiters to separate words in a string.

By default, the IFS variable is set to include the whitespace characters: space, tab, and newline. This means that when you use variables or command substitutions, the shell will split the resulting string into separate words based on these whitespace characters.

However, you can customize the IFS variable to use different delimiters when splitting strings into words. This is particularly useful when you want to split a string using specific characters like commas, colons, semicolons, etc.

In this example, we set the IFS on the same line as the read command. The scope of the IFS change is limited to this read command only, and it doesn’t affect other parts of the script or subsequent commands.

This feature is convenient because it automatically restores the IFS to its previous value after the read command executes, without any additional manual handling. It’s an effective and clean way to split strings into arrays without worrying about unintended side effects on the IFS setting in the rest of your script.

Using IFS variable and array assignment

#!/bin/bash

# Input string
my_string="apple,banana,orange"

# Set IFS and use array assignment
IFS=',' my_array=($my_string)

# Print each element of the array
for element in "${my_array[@]}"; do
  echo "$element"
done

This method uses an array assignment with the IFS variable set to , as a delimiter to split the string.

This line my_array=($my_string) performs an array assignment. It takes the value of the variable my_string and splits it into separate elements based on the IFS delimiter. Each part of the string separated by , will become an element in the my_array.

Using tr command

Another method is to use the tr (translate) command to replace the delimiter character with a newline and then store the output in an array. For example:

#!/bin/bash

# Input string
my_string="apple,banana,orange"

# Use tr command to replace the delimiter character with a newline
my_array=($(echo $my_string | tr "," "\n"))

# Print each element of the array
for element in "${my_array[@]}"; do
  echo "$element"
done

This part of the command tr "," "\n" uses the tr command to perform character translation. It replaces all occurrences of the comma , with the newline character \n. This effectively converts the comma-separated string into a newline-separated string.

Command substitution $(...) allows the output of the enclosed command to be captured and used as part of the outer command. In this case, the output of echo $my_string | tr "," "\n" will be used as input for the array assignment.

The output is treated as a list of elements separated by whitespace, and each element will become an element of the array.

However, it’s important to note that this method has some limitations. It may not handle strings with spaces or special characters correctly since the tr command uses spaces to separate elements. Additionally, if the string contains newlines, the array elements may not be split as expected. For more complex scenarios, using IFS and read is generally more reliable for splitting strings into arrays in Bash.