1

Normally, looping over the files I use basename to extract the name of the file as a separate variable:

# remove .pdb extension from filename in new variable and print name of the file without it
for pdb in "${storage}"/complex*.pdb ; do
pdb_name=$(basename "$pdb" .pdb)
echo this is "$pdb_name" without its extension!
done

How could I remove several patterns from each file using the same basename expression? For instance, in addition to ".pdb" I would like to omit also "complex", which is always present at the beginning of each file (here I used it as a pattern to recognize file in for LOOP).

1 Answer 1

3

As far as I know, basename can not remove a prefix from the non-directory portion of a path. I would suggest using parameter expansion features instead:

shopt -s nullglob   # Don't loop over the pattern if it matches nothing
for pdb in "$storage"/complex*.pdb
do
  pdb_name=${pdb##*/complex}
  pdb_name=${pdb_name%.pdb}
  printf '%s\n' "$pdb_name"
done

${pdb##*/complex} expands to the value of pdb with the longest prefix that matches the */complex shell pattern removed.

${pdb_name%.pdb} expands to the value of pdb_name with the shortest suffix matching the .pdb shell pattern removed.

While this is not an issue in your case, note that base_name=$(basename "$path") strips newline characters at the end of file names (because of command substitution) as a likely unwanted side effect. Shell parameter expansion is safer in this respect.

2
  • thank you! as I understood correclt it is not possible to do those two editions in one basename command, isn't it ? Commented Oct 21, 2020 at 9:53
  • As far as I know, no, basename can't remove a prefix from the last component of a path. Commented Oct 21, 2020 at 9:58

You must log in to answer this question.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.