Подтвердить что ты не робот

Как читать файл из строки x в конец файла в bash

Мне бы хотелось узнать, как я могу прочитать каждую строку файла csv со второй строки до конца файла в bash script.

Я знаю, как читать файл в bash:

while read line
 do   
   echo -e "$line\n"
done < file.csv

Но я хочу прочитать файл, начиная со второй строки до конца файла. Как я могу достичь этого?

4b9b3361

Ответ 1

tail -n +2 file.csv

На странице :

-n, --lines=N
     output the last N lines, instead of the last 10
...

If the first character of N (the number of bytes or lines)  is  a  '+',
print  beginning with the Nth item from the start of each file, other-
wise, print the last N items in the file.

По-английски это означает, что:

tail -n 100 печатает последние 100 строк

tail -n +100 печатает все строки, начиная с строки 100

Ответ 2

Простое решение с sed:

sed -n '2,$p' <thefile

где 2 - номер строки, которую вы хотите прочитать.

Ответ 3

Или иначе (чистый bash)...

{ for ((i=1;i--;));do read;done;while read line;do echo $line;done } < file.csv

Лучше написано:

linesToSkip=1
{
    for ((i=$linesToSkip;i--;)) ;do
        read
        done
    while read line ;do
        echo $line
        done
} < file.csv

Эта работа, даже если linesToSkip == 0 или linesToSkip > file.csv количество строк

Edit

Изменен () для {}, поскольку gniourf_gniourf предписывает мне рассмотреть: Первый синтаксис генерирует под-оболочку, whille {} do not.

конечно, для пропуска только одной строки (в качестве исходного заголовка вопроса) петлю for (i=1;i--;));do read;done можно просто заменить на read:

{ read;while read line;do echo $line;done } < file.csv

Ответ 4

В зависимости от того, что вы хотите делать с вашими линиями: если вы хотите сохранить каждую выделенную строку в массиве, лучшим выбором является встроенный mapfile:

numberoflinestoskip=1
mapfile -s $numberoflinestoskip -t linesarray < file

будет хранить каждую строку файла file, начиная с строки 2, в массиве linesarray.

help mapfile для получения дополнительной информации.

Если вы не хотите хранить каждую строку в массиве, хорошо, есть и другие очень хорошие ответы.

Как указывает Ф. Хаури в комментарии, это применимо только в том случае, если вам нужно сохранить весь файл в памяти.

В противном случае лучше всего:

{
    read; # Just a scratch read to get rid (pun!) of the first line
    while read line; do
        echo "$line"
    done
} < file.csv

Примечание: там не требуется/нуждается в подлесте.

Ответ 5

Существует много решений. Один из моих любимых:

(head -2 > /dev/null; whatever_you_want_to_do) < file.txt

Вы также можете использовать tail, чтобы пропустить нужные строки:

tail -n +2 file.txt | whatever_you_want_to_do

Ответ 6

Я бы просто получил переменную.

#!/bin/bash

i=0
while read line
do
    if [ $i != 0 ]; then
      echo -e $line
    fi
    i=$i+1
done < "file.csv"

ОБНОВЛЕНИЕ Выше будет проверяться переменная $i в каждой строке csv. Поэтому, если у вас есть очень большой файл csv из миллионов строк, он будет потреблять значительное количество циклов процессора, не подходит для природы матери.

После того, как один liner можно использовать для удаления самой первой строки файла CSV с помощью sed, а затем вывести оставшийся файл в цикл while.

sed 1d file.csv | while read d; do echo $d; done

Ответ 7

Это будет работать

i=1
while read line
 do   
   test $i -eq 1 && ((i=i+1)) && continue
   echo -e "$line\n"
done < file.csv