189

How do I find the length of an array in shell?

For example:

arr=(1 2 3 4 5)

And I want to get its length, which is 5 in this case.

codeforester
  • 39,467
  • 16
  • 112
  • 140
Arunachalam
  • 5,417
  • 20
  • 52
  • 80

7 Answers7

256
$ a=(1 2 3 4)
$ echo ${#a[@]}
4
codeforester
  • 39,467
  • 16
  • 112
  • 140
ghostdog74
  • 327,991
  • 56
  • 259
  • 343
  • 13
    What does `@` do here? – Ahmed Akhtar May 29 '17 at 07:50
  • 18
    @AhmedAkhtar There's a decent explanation [here](https://stackoverflow.com/a/3355375/1858225). Basically, `[*]` and `[@]` both "explode" arrays into a tokenized string, but `[@]` can preserve spaces *within* tokens. However, when *counting* elements, it doesn't appear to matter; `arr=(foo "bar baz"); echo ${arr[*]}` prints `2`, not `3`. – Kyle Strand May 23 '18 at 19:56
  • 1
    This worked for me but only after removing `[@]` on Mac. `GNU bash, version 3.2.57(1)-release (x86_64-apple-darwin19)` if anyone's having the same issue. – Prav Jul 21 '20 at 16:54
  • 1
    Without the `[@]` it returns the length of the first element for me (using Bash 4.4.20(1)-release). – Sussch Nov 03 '20 at 08:44
  • 4
    @PraveenPremaratne I tested `${#a[@]}` in bash 2.00.0(2) (the oldest version I could compile. This is from 1996!) and bash 3.2.57(1) (the version used on macOS). The command worked as expected in both version. I guess you must have made an error somewhere else. – Socowi Aug 17 '21 at 11:19
  • 1
    @Socowi I just checked it as standalone and it works for me as well, it was probably somewhere else on the script that conflicted the `[`. – Prav Aug 17 '21 at 13:42
47

From Bash manual:

${#parameter}

The length in characters of the expanded value of parameter is substituted. If parameter is ‘’ or ‘@’, the value substituted is the number of positional parameters. If parameter is an array name subscripted by ‘’ or ‘@’, the value substituted is the number of elements in the array. If parameter is an indexed array name subscripted by a negative number, that number is interpreted as relative to one greater than the maximum index of parameter, so negative indices count back from the end of the array, and an index of -1 references the last element.

Length of strings, arrays, and associative arrays

string="0123456789"                   # create a string of 10 characters
array=(0 1 2 3 4 5 6 7 8 9)           # create an indexed array of 10 elements
declare -A hash
hash=([one]=1 [two]=2 [three]=3)      # create an associative array of 3 elements
echo "string length is: ${#string}"   # length of string
echo "array length is: ${#array[@]}"  # length of array using @ as the index
echo "array length is: ${#array[*]}"  # length of array using * as the index
echo "hash length is: ${#hash[@]}"    # length of array using @ as the index
echo "hash length is: ${#hash[*]}"    # length of array using * as the index

output:

string length is: 10
array length is: 10
array length is: 10
hash length is: 3
hash length is: 3

Dealing with $@, the argument array:

set arg1 arg2 "arg 3"
args_copy=("$@")
echo "number of args is: $#"
echo "number of args is: ${#@}"
echo "args_copy length is: ${#args_copy[@]}"

output:

number of args is: 3
number of args is: 3
args_copy length is: 3
codeforester
  • 39,467
  • 16
  • 112
  • 140
26

Assuming bash:

~> declare -a foo
~> foo[0]="foo"
~> foo[1]="bar"
~> foo[2]="baz"
~> echo ${#foo[*]}
3

So, ${#ARRAY[*]} expands to the length of the array ARRAY.

unwind
  • 391,730
  • 64
  • 469
  • 606
9

in tcsh or csh:

~> set a = ( 1 2 3 4 5 )
~> echo $#a
5
Rahul
  • 123
  • 1
  • 5
6

In the Fish Shell the length of an array can be found with:

$ set a 1 2 3 4
$ count $a
4
matli
  • 27,922
  • 6
  • 37
  • 37
harm
  • 10,045
  • 10
  • 36
  • 41
5

This works well for me:

arglen=$#
argparam=$*
if [ $arglen -eq '3' ];
then
    echo Valid Number of arguments
    echo "Arguments are $*"
else
    echo only four arguments are allowed
fi
Aaron Meese
  • 1,670
  • 3
  • 22
  • 32
Mansur Ul Hasan
  • 2,898
  • 27
  • 24
-6

For those who still searching a way to put the length of an array into a variable:

foo="${#ARRAY[*]}"
Antoine Viallon
  • 314
  • 4
  • 12