substitute file names using rename

2020-01-19 06:24发布

问题:

I want to rename files names by substituting all the characters starting from "_ " followed by eight capital letter and keep only the extension.

4585_10_148_H2A119Ub_GTCTGTCA_S51_mcdf_mdup_ngsFlt.fm
4585_10_148_H3K27me3_TCTTCACA_S51_mcdf_mdup_ngsFlt.fm
4585_27_128_Bap1_Bethyl_ACAGATTC_S61_mcdf_mdup_ngsFlt.fw
4585_32_148_1_INPUT_previous_AGAGTCAA_S72_mcdf_mdup_ngsFlt.bw

expected output

4585_10_148_H2A119Ub.fm
4585_10_148_H3K27me3.fm
4585_27_128_Bap1_Bethyl.fm
4585_32_148_1_INPUT_previous.fm

回答1:

Try this:

for f in *; do
    target=$(echo "${f}" | sed -E 's/_[[:upper:]]{8}.*\././')
    mv "${f}" "${target}"
done

The key thing is the -E argument to sed, since it enables expanded regular expressions.



回答2:

You can also use rename (a.k.a. prename or Perl rename) like this:

rename --dry-run 's|_[[:upper:]]{8}.*\.|.|' *

Sample Output

'4585_10_148_H2A119Ub_GTCTGTCA_S51_mcdf_mdup_ngsFlt.fm' would be renamed to '4585_10_148_H2A119Ub.fm'
'4585_32_148_1_INPUT_previous_AGAGTCAA_S72_mcdf_mdup_ngsFlt.bw' would be renamed to '4585_32_148_1_INPUT_previous.bw'

Remove the --dry-run and run again for real, if the output looks good.

This has several added benefits:

  • that it will warn and avoid any conflicts if two files rename to the same thing,
  • that it can rename across directories, creating any necessary intermediate directories on the way,
  • that you can do a dry run first to test it,
  • that you can use arbitrarily complex Perl code to specify the new name.

On a Mac, install it with homebrew using:

brew install rename


回答3:

You may try this.

for i in *.fm; do mv $i $(echo $i | sed 's/_GTCTGTCA_S51_mcdf_mdup_ngsFlt//g'); done;
for i in *.fm; do mv $i $(echo $i | sed 's/_TCTTCACA_S51_mcdf_mdup_ngsFlt//g'); done;


标签: shell sed rename