Нумеровать кучу файлов по временной метке даты изменения?

Предполагая, что это 9-я вкладка -поле с разделителями файла GFF(поле «атрибуты» ), вы можете извлечь значение атрибута gene, соответствующее конкретному IDатрибут (читается из отдельного файла )вот так сawk:

BEGIN { FS = "\t" }

FNR == NR {
    # Read IDs into a hash as keys.
    ids[$1] = 1
    next
}

$3 == "gene" {
    # Split the attribute field into separate key-value pairs.
    n = split($9, keyvalues, ";")

    id = ""    # Not found a gene ID yet
    gene = ""  # No gene name to print

    # Loop over the key-value pairs, split them on the "="
    # and extract the gene name and gene ID.
    for (i = 1; i <= n; ++i) {
        split(keyvalues[i], attr, "=")
        if (attr[1] == "ID") {
            if (attr[2] in ids)
                id = attr[2]
            else
                next  # This line is not of interest
        }
        else if (attr[1] == "gene")
            gene = attr[2]
    }

    if (id != "" && gene != "")
        print gene
}

Запуск этого в файле GFF с именем file.gff, содержащем заданные данные в столбце 9 и со списком идентификаторов генов в id.list:

.

$ awk -f script.awk id.list file.gff
LOC108565285
LOC108569527

Список идентификаторов генов считывается из первого файла в блоке FNR == NRв коде awk, тогда как последний блок обрабатывает атрибутивное поле характерных линий генов (только )во втором (и все последующие )файлы, заданные в командной строке.

Код awkпредполагает, что атрибуты IDи geneфайла GFF содержат только одно значение (без запятой -список значений с разделителями )и что значения не цитируется.

Чтобы получить вывод в виде списка имен генов и идентификаторов генов (два столбца ), измените оператор print geneна print id, gene.

0
12.05.2021, 21:14
3 ответа

Сzsh:

autoload zmv
n=0; zmv -n '*(#qOm)' '${(l[3][0])$((++n))}_$f'

(снять-n(для работы всухую -запустить всухую )при хорошем состоянии ).

Это:

  • zmv:автозагружаемая функция для переименования файлов с использованием расширенных шаблонов zsh и операторов подстановки
  • *:все не -скрытые файлы в текущем каталоге
  • (#q...):многословная форма введения квалификаторов glob
  • Om:порядок в обратном порядке по возрасту. Итак, новейшее последнее.
  • ${(l[3][0])$((++n))}:слева -дополняет расширение $((++n))по ширине 3 нулями.
  • _$fи добавьте _и исходное имя файла
1
28.07.2021, 11:33

Нашел решение здесь .

ls -1tr | rename -v 's/.*/our $i;if(!$i){$i=1;} sprintf("%04d.pdf", $i++)/e'

0
28.07.2021, 11:33
find. -type f -printf '%C@ %p\0' |
  sort -z -n |
  awk  'BEGIN{RS=ORS="\0"};{print $2}' | 
  rename -0 -n 'our $i;
                s:(^.*/)([^/]*):sprintf("%s%04d_%s",$1,++$i,$2):e'

Это использует GNU findдля печати имен файлов, разделенных NUL (%p, поэтому полный путь )с префиксом их отметки времени модификации(%C@)и символом пробела в секундах unix -, поскольку --] числовой формат эпохи.

При необходимости вы можете использовать любую из других опций findздесь, чтобы уточнить поиск файлов (, например. -name "*.pdf", -maxdepth 2и т. д.)

Затем выходные данные

findпередаются в GNU sortс использованием параметров -z -nдля сортировки NUL-разделенных входных данных -численно (по временным меткам ), а затем в awk для удаления временной метки и space, а затем, наконец, передается в сценарий переименования perl.

Perl-скрипт переименования использует параметр -0для чтения записей, разделенных NUL, из стандартного ввода, а затем:

  • использует sprintf()с '%s%04d _%s'(%04d_заполняет нулями -, 4 цифры шириной и подчеркиванием ), используя $iв качестве счетчика для замены имени файла часть имени.

    $1— часть пути полного имени файла, $++i— переменная счетчика с автоматическим -приращением, а $2— базовое имя файла.

  • $iобъявляется с our, чтобы сделать ее глобальной переменной, поэтому она сохраняет свое значение для каждой итерации цикла (, в противном случае она сбрасывается в ноль каждый раз ).

Опция -nпревращает это в пробный -запуск, так что отображается только то, что будет переименовано. Как только вы убедитесь, что он будет делать то, что вы хотите, удалите -n, чтобы незаметно переименовать файлы без вывода, или замените его на -vдля подробного вывода.

В отличие от использования ls -1trэто будет НЕ прерываться, если любое из имен файлов содержит символы новой строки. Он будет работать с любым допустимым именем файла.


К вашему сведению, чтобы добавить хорошо отформатированную -дату к каждому имени файла, см. мой сценарий renameв Переименование группы файлов с отметкой времени изменения даты в конце имени файла? .Это легко изменить, чтобы добавить к имени файла префикс даты и времени. Он запускает statдля каждого файла, чтобы получить метку времени, поэтому имена файлов не нужно предварительно -сортировать.

напр.

rename -n 'BEGIN {use Date::Format};
           die $! unless -f $_;
           next if (m/^\d{8}-$/);
           my $ts=(stat($_))[9];
           my $dt=time2str("%Y%m%d-%H%M%S",$ts);
           $_ = "$dt-$_"' *.pdf
1
28.07.2021, 11:33

Теги

Похожие вопросы