nanker
nanker

Reputation: 603

find option available to omit leading './' in result

I think this is probably a pretty n00ber question but I just gotsta ask it. When I run:

$ find . -maxdepth 1 -type f \( -name "*.mp3" -o -name "*.ogg" \)

and get:

./01.Adagio - Allegro Vivace.mp3
./03.Allegro Vivace.mp3
./02.Adagio.mp3
./04.Allegro Ma Non Troppo.mp3 

why does find prepend a ./ to the file name? I am using this in a script:

fList=()
while read -r -d $'\0'; do
    fList+=("$REPLY")
done < <(find . -type f \( -name "*.mp3" -o -name "*.ogg" \) -print0)
fConv "$fList" "$dBaseN"

and I have to use a bit of a hacky-sed-fix at the beginning of a for loop in function 'fConv', accessing the array elements, to remove the leading ./. Is there a find option that would simply omit the leading ./ in the first place?

Upvotes: 1

Views: 113

Answers (4)

David W.
David W.

Reputation: 107090

If your -maxdepth is 1, you can simply use ls:

$ ls *.mp3 *.ogg

Of course, that will pick up any directory with a *.mp3 or *.ogg suffix, but you probably don't have such a directory anyway.

Another is to munge your results:

$ find . -maxdepth 1 -type f \( -name "*.mp3" -o -name "*.ogg" \) | sed 's#^\./##'

This will remove all ./ prefixes, but not touch other file names. Note the ^ anchor in the substitution command.

Upvotes: 1

that other guy
that other guy

Reputation: 123650

If you ask it to search under /tmp, the results will be on the form /tmp/file:

$ find /tmp
/tmp
/tmp/.X0-lock
/tmp/.com.google.Chrome.cUkZfY

If you ask it to search under . (like you do), the results will be on the form ./file:

$ find .
.
./Documents
./.xmodmap

If you ask it to search through foo.mp3 and bar.ogg, the result will be on the form foo.mp3 and bar.ogg:

$ find *.mp3 *.ogg
click.ogg
slide.ogg
splat.ogg

However, this is just the default. With GNU and other modern finds, you can modify how to print the result. To always print just the last element:

find /foo -printf '%f\0'

If the result is /foo/bar/baz.mp3, this will result in baz.mp3.

To print the path relative to the argument under which it's found, you can use:

find /foo -printf '%P\0'

For /foo/bar/baz.mp3, this will show bar/baz.mp3.

However, you shouldn't be using find at all. This is a job for plain globs, as suggested by R Sahu.

shopt -s nullglob
files=(*.mp3 *.ogg)
echo "Converting ${files[*]}:"
fConv "${files[@]}"

Upvotes: 2

R Sahu
R Sahu

Reputation: 206717

find . -maxdepth 1 -type f \( -name "*.mp3" -o -name "*.ogg" \) -exec basename "{}" \;

Having said that, I think you can use a simpler approach:

for file in *.mp3 *.ogg
do
   if [[ -f $file ]]; then
       # Use the file
   fi
done

Upvotes: 2

exPHAT
exPHAT

Reputation: 128

The ./ at the beginning of the file is the path. The "." means current directory.

You can use "sed" to remove it.

find . -maxdepth 1 -type f \( -name "*.mp3" -o -name "*.ogg" \) | sed 's|./||'

I do not recommend doing this though, since find can search through multiple directories, how would you know if the file found is located in the current directory?

Upvotes: 3

Related Questions