Copy files on a list to another directory

Hi.

I have a list with file names like

testfile1.wav
testfile2.wav
testfile3.wav

and a folder that contains a large number of wav files (not only the ones on the list).

I would like to copy the files whose names are on the list from the wav file directory to a new directory.

I tried to write a Python script for this, but it doesn't work and I wondered if there's an easier option to do that.

Cheers,

Kat

If GNU cp is available (if you're on Linux for example) and if the filenames do not contain pathological characters (newlines or white spaces):

< list xargs cp -t target_dir --

If the filenames contain white spaces and you have GNU cp (this is will be much slower if the number of files is high):

< list xargs -I{} cp -t target_dir -- {}

This is similar, but noisy:

while IFS= read -r; do 
  cp -- "$REPLY" target_dir 
done < list

Another option, if the filenames do not contain embedded newlines
and the total length of their names is below the ARGS_MAX limit
of your system:

( IFS=$'\n'; cp -- $(<list) target_dir )

If your shell doesn't expand ansi strings $'...' , use a literal newline:

( 
  IFS='
' 
  cp -- $(<list) target_dir 
  )
1 Like

Thanks! I tried the first option but I received the error

cp: target `testfile.wav' is not a directory

I executed it like this:

cd'ed into the wav file directory and then:

< ../list.data xargs cp -- -t ./target_directory

Sorry, there was an error in the commands I posted. Try the new versions.
The double dash -- marks the end of options, so it should be after the -t option and its argument.

Hi,
I didnt understand what is difficult in this.. I have a suggestion.

for file in `cat list_file `                          /* list_file contains the wav files you want to copy
 do 
 cp source_dir/$file new_dir
 done

That is a useless use of cat and useless use of backticks, inherently dangerous because any file too long for a shell variable to hold will have some of its contents silently lost. It's also very inefficient. There's a much better way to do this, which doesn't attempt to store the entire file in memory at once, and uses pure shell built-ins:

while read LINE
do
        ...
done < filename
1 Like