Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

bash for loop with numerated names

I'm currently working on a maths project and just run into a bit of a brick wall with programming in bash.

Currently I have a directory containing 800 texts files, and what I want to do is run a loop to cat the first 80 files (_01 through to _80) into a new file and save elsewhere, then the next 80 (_81 to _160) files etc.

all the files in the directory are listed like so: ath_01, ath_02, ath_03 etc.

Can anyone help?

So far I have:

#!/bin/bash

for file in /dir/*

do
echo ${file}
done

Which just simple lists my file. I know I need to use cat file1 file2 > newfile.txt somehow but it's confusing my with the numerated extension of _01, _02 etc.

Would it help if I changed the name of the file to use something other than an underscore? like ath.01 etc?

Cheers,

like image 204
gray_fox Avatar asked Dec 12 '22 17:12

gray_fox


1 Answers

Since you know ahead of time how many files you have and how they are numbered, it may be easier to "unroll the loop", so to speak, and use copy-and-paste and a little hand-tweaking to write a script that uses brace expansion.

#!/bin/bash

cat ath_{001..080} > file1.txt
cat ath_{081..160} > file2.txt
cat ath_{161..240} > file3.txt
cat ath_{241..320} > file4.txt
cat ath_{321..400} > file5.txt
cat ath_{401..480} > file6.txt
cat ath_{481..560} > file7.txt
cat ath_{561..640} > file8.txt
cat ath_{641..720} > file9.txt
cat ath_{721..800} > file10.txt

Or else, use nested for-loops and the seq command

N=800
B=80
for n in $( seq 1 $B $N ); do
    for i in $( seq $n $((n+B - 1)) ); do
       cat ath_$i
    done > file$((n/B + 1)).txt
done

The outer loop will iterate n through 1, 81, 161, etc. The inner loop will iterate i over 1 through 80, then 81 through 160, etc. The body of the inner loops just dumps the contents if the ith file to standard output, but the aggregated output of the loop is stored in file 1, then 2, etc.

like image 67
chepner Avatar answered Dec 20 '22 01:12

chepner