-1

I have multipe files containing errors in annual reports. Each file name have .mvt extension. It is not necessary that every file has error. I have found that when errors appear OR not there is always header in the file, which is 5 lines. It is not necessary to see every file (more than 300 files).

I wonder if awk can be helpful like awk 'NR> 5' filename.mvt, but problem is that I have to test each file with if else. I want to copy (with cp command) files, so name remain the same, files that contain more than 5 line.

closed as too broad by Prvt_Yadv, Rui F Ribeiro, Romeo Ninov, msp9011, Mr Shunz Apr 15 at 9:37

Please edit the question to limit it to a specific problem with enough detail to identify an adequate answer. Avoid asking multiple distinct questions at once. See the How to Ask page for help clarifying this question. If this question can be reworded to fit the rules in the help center, please edit the question.

  • It strikes me as more useful to look in the files for the actual error (if it can be detected), than to scan the files for the consequence of the error. What is the error, and how have you determined that some files contain it and some don't, or is the only error that some files are "longer than others"? – Kusalananda Apr 13 at 7:39
  • I mentioned that system creating files for each movment. Every file is starting with header and header are almosst common and contains 5 line. So i realized that if file has more than 5 lines that indicate it contains error. – Kalpesh Bhoj Apr 13 at 15:49
1

The following command will detect all regular file in or below the current directory that has names ending in .mvt and that are longer than five lines. For each of those files, it will output the file's pathname.

find . -type f -name '*.mvt' -exec sh -c '
    for pathname do
        if [ "$( wc -l <"$pathname" )" -gt 5 ]; then
            printf "%s\n" "$pathname"
        fi
    done' sh {} +

To copy each of those files to some directory (it is unclear what you actually want to do with these files), you may want to do the following:

mkdir -p possible-error-files || exit 1

find . -type f -name '*.mvt' -exec sh -c '
    for pathname do
        if [ "$( wc -l <"$pathname" )" -gt 5 ]; then
            printf "%s\n" "$pathname"
            cp "$pathname" possible-error-files
        fi
    done' sh {} +

In both commands, I pass the contents of the file to wc -l count the number of lines.

As an alternative, you may use awk to do both the counting of lines and the output of the pathname (modifying the second command from above):

mkdir -p possible-error-files || exit 1

find . -type f -name '*.mvt' -exec sh -c '
    for pathname do
        if awk "BEGIN { err=1 } FNR > 5 { print FILENAME; err=0; exit } END { exit err }" <"$pathname"
        then
            cp "$pathname" possible-error-files
        fi
    done' sh {} +

Or, with GNU awk:

mkdir -p possible-error-files || exit 1

find . -type f -name '*.mvt' -exec awk '
    FNR > 5 {
        print FILENAME
        system("cp \"" FILENAME "\" possible-error-files")
        nextfile
    }' {} +
1

Here's another solution:

for mvt_file in *.mvt; do
    if [ "$(awk 'END {if(NR > 5) print "yes"}' "$mvt_file")" == "yes" ]; then
        cp "$mvt_file" "$mvt_file - copy"
    fi
done

You can also do:

for mvt_file in *.mvt; do
    if [ "$(wc -l < "$mvt_file")" -gt 5 ]; then
        cp "$mvt_file" "$mvt_file - copy"
    fi
done

Either should work fine.

0

We can use below script to find the file which having more than 5 lines

for i in filename1 filename2 filename3 file; do j=`awk '{print NR}' $i| sort -nr| sed -n '1p'`; if [[ $j  > 5 ]]; then echo $i; fi; done| sed '1i below are filenames which having lines more than 5'
  • Note that the awk command could simply be awk 'FNR>5 { print FILENAME; exit }'. – Kusalananda Apr 13 at 8:06
  • Thanks for feed back yes i agree with your comment – Praveen Kumar BS Apr 13 at 8:07

Not the answer you're looking for? Browse other questions tagged or ask your own question.