3

I have a shell variable sampleDir:

sampleDir=/home/sample*
echo $sampleDir

will give:

/home/sample_001 /home/sample_002 /home/sample_003

(note there are sub-directories under the sample_*** ones)

If I would like to count how much of these items are in this $sampleDir variable, what would be a best way please? (Expect to return 3)

Mad Physicist
  • 107,652
  • 25
  • 181
  • 264
Helene
  • 953
  • 3
  • 12
  • 22

3 Answers3

5

Store the variables in an array:

sampleDir=(/home/sample*)

Use Parameter Expansion to get count of items in array:

echo "${#sampleDir[@]}"
rigglesbee
  • 108
  • 4
3

sampleDir=/home/sample* assigns a literal '/home/sample*' into sampleDir

$ echo "$sampleDir" 
/home/sample*

but if you don't double-quote the variable expansion, it will undergo glob expansion (unless set -f is on) and splitting on $IFS characters (characters in the IFS variable— normally space, tab, and newline).

You can count the number of items after the expansion by passing the unquoted $sampleDir to a function that counts its arguments.

argc() { argc=$#; } 
argc $sampleDir
echo $argc      #will print the number of items $sampleDir expanded to 

This would be how you can do it portably, on any POSIX shell (solutions based on things like arrays are limited to shells that have them).


( I recommend returning stuff from shell functions by assigning it to a global variable of the same name as the function. It's portable, namespace-clean, and very fast (unlike echoing and then using captures to get the echoed string, which is common, but rather expensive))

Petr Skocik
  • 58,047
  • 6
  • 95
  • 142
2

As posed, you are trying to count the number of spaces in your string and add one. There are a number of good ways of doing this. The shortest to type is probably something along the lines of

COUNT=$(grep -o ' ' <<< "$sampleDir" | wc -l)
((COUNT++))

The problem with this approach is that you can not have spaces anywhere in the file names. A better way might be to just store the name of the directory you are interested in and run a command like find on that:

sampleRoot=/home
find "$sampleRoot" -name 'sample*' | wc -l
Mad Physicist
  • 107,652
  • 25
  • 181
  • 264