← Back to DevBytes

Fish Scripting: Arrays Complete Guide

What Are Arrays in Fish?

In the Fish shell, arrays are a fundamental data structure for storing ordered collections of values. Fish uses the term lists interchangeably with arrays, but they behave as indexed arrays where each element is a string. An array can hold any number of elements, and each element is accessed via an index starting at 1 (unlike many programming languages that use 0-based indexing).

Arrays are crucial for handling multiple arguments, file names, command outputs, and building complex scripts. Fish provides a rich set of built-in commands and syntax to manipulate arrays with ease.

Why Arrays Matter in Fish Scripting

🚀 Deploy your AI agent in 10 minutes

Managed Hermes hosting. Zero DevOps. 100M tokens/mo included.

Try it free →

Understanding arrays unlocks the ability to:

Creating and Initializing Arrays

Fish uses the set command to define and assign values to variables. To create an array, assign multiple values inside parentheses, separated by spaces:

set my_array value1 value2 value3

If you need elements that contain spaces, you must quote them:

set my_array "value with spaces" 'another element' plain

Empty array:

set empty_array

Or using the -l (list) option (explicit):

set -l my_local_array element1 element2

You can also assign the output of a command to an array using command substitution in parentheses:

set files (ls)

This captures each line of ls as a separate array element.

Preserving Newlines in Command Substitution

To preserve literal newlines in the output (treat the whole output as a single element or split by newlines correctly), use the -f or --fields option with set and string split. However, for most cases, (command) splits on newlines. To capture exact lines without trimming, use set lines (cat file | string split \n).

Accessing Array Elements

Fish uses 1-based indexing. To access a specific element:

echo $my_array[1]  # first element

To get all elements, simply use $my_array (no brackets). Each element becomes a separate argument:

printf "%s\n" $my_array  # prints each element on its own line

To get the length of an array, use count:

count $my_array

Or store the count:

set len (count $my_array)

Slicing Arrays

You can extract a range of elements using the syntax $array[start..end]:

set sublist $my_array[2..4]  # elements 2 through 4

Omitting end goes to the last element:

set tail $my_array[3..]  # elements from 3 to end

Modifying Arrays

Appending Elements

Use the set -a or set --append flag:

set -a my_array "new element"

Or:

set --append my_array another_item

Prepending Elements

Use set -p or set --prepend:

set -p my_array "first element"

Removing Elements by Index

Use the -e or --erase flag with the variable name and index:

set -e my_array[2]  # removes the second element

You can remove a range:

set -e my_array[1..3]

Removing Elements by Value

Fish doesn't have a built-in direct remove-by-value, but you can use set with a filter or string match to create a new array without the unwanted element:

set my_array (string match -v "unwanted" $my_array)

The -v flag inverts the match, returning elements that do not match the pattern.

Replacing Values

Use string replace or a loop. To replace all occurrences of a substring:

set my_array (string replace -a "old" "new" $my_array)

Iterating Over Arrays

Fish's for loop works naturally with arrays:

for item in $my_array
    echo "Item: $item"
end

To iterate with an index:

for i in (seq (count $my_array))
    echo "Index $i: $my_array[$i]"
end

Or using the index in the loop variable:

set index 1
for item in $my_array
    echo "Item $index: $item"
    set index (math $index + 1)
end

Associative Arrays / Key-Value Lists

Fish does not have native associative arrays like Bash. However, you can simulate them using two synchronized arrays or a single array with alternating key-value pairs. A common pattern is to store keys and values in separate lists or use the set command to store structured data.

For example, storing key-value pairs in a single list:

set -l config key1 value1 key2 "value with spaces" key3 value3

Then retrieve by searching for the key index and getting the next element. This is cumbersome, so many users leverage fish's ability to define functions with named arguments or use external files. For more complex data, consider using JSON and the jq utility.

Array Best Practices

Conclusion

Fish's array handling is intuitive and powerful, with a clean syntax that avoids many pitfalls found in other shells. Mastering arrays enables you to write robust, efficient scripts that can handle complex data flows. Remember the 1-based indexing, the use of set with append/prepend flags, and the seamless integration with loops and command substitution. With practice, arrays will become a natural part of your Fish scripting toolkit.

🚀 Need a reliable AI agent for your project?

Deploy Hermes Agent in 10 minutes. Managed hosting, zero DevOps.

Get Started — $23.99/mo
← Back to all articles