${ ... } (chaves) marca vários tipos de expansão de parâmetros , a mais simples das quais é apenas expandir o valor de uma variável. O material entre chaves não é um nome de parâmetro válido, ou qualquer outra expansão, então o shell reclama.
Parece que você quer a substituição de comandos, por isso, a sintaxe é $( ... ) (parênteses regulares).
Além disso, o ls em ls $filename | sed... parece um pouco desnecessário, a variável é expandida para o nome do arquivo e ls apenas a passa. Você poderia usar apenas echo "$filename" | sed ... .
Dito isso, você pode fazer essas modificações diretamente no shell:
no=${filename/assemblyDB.} # remove first match
no=${no/.las}
ou, usando os operadores padrão:
no=${filename#assemblyDB.} # remove from start of string
no=${no%.las} # remove from end of string
Se você executar sed , convém observar que . corresponde a qualquer caractere em expressões regulares, por isso seria mais correto citá-lo com uma barra invertida. Além disso, você pode dar a um sed instance ambos os comandos: sed -e 's/assemblyDB\.//' -e 's/\.las//' .
E, em seguida, for filename in $(find . -type f -name "assemblyDB.*.las"); do tem os problemas de analisar ls , principalmente o fato de que espaços em branco e curingas nos nomes dos arquivos vão quebrar isto. No ksh / Bash / zsh, você poderia fazer todo esse loop no shell:
shopt -s globstar # in Bash
for filename in **/assemblyDB.*.las; do
...