解析唯一数据和重命名文件
Posted
技术标签:
【中文标题】解析唯一数据和重命名文件【英文标题】:Parsing unique data and renaming files 【发布时间】:2022-01-19 00:51:18 【问题描述】:我试图创建一个 Perl 脚本来重命名文件(数百个不同名称的文件),但我没有成功。我首先需要找到唯一的文件编号,然后将其重命名为更易于阅读的名称。由于文件名不连续,因此很难。
文件名示例:重要性数在que序列之后
# vv-- this number
lane8-s244-index--ATTACTCG-TATAGCCT-01_S244_L008_R1_001.fastq
lane8-s245-index--ATTACTCG-ATAGAGGC-02_S245_L008_R1_001.fastq
lane8-s246-index--TCCGGAGA-TATAGCCT-09_S246_L008_R1_001.fastq
lane8-s247-index--TCCGGAGA-ATAGAGGC-10_S247_L008_R1_001.fastq
lane8-s248-index--TCCGGAGA-CCTATCCT-11_S248_L008_R1_001.fastq
lane8-s249-index--TCCGGAGA-GGCTCTGA-12_S249_L008_R1_001.fastq
lane8-s250-index--TCCGGAGA-AGGCGAAG-13_S250_L008_R1_001.fastq
lane8-s251-index--TCCGGAGA-TAATCTTA-14_S251_L008_R1_001.fastq
lane7-s0007-index--ATTACTCG-TATAGCCT-193_S7_L007_R1_001.fastq
lane7-s0008-index--ATTACTCG-ATAGAGGC-105_S8_L007_R1_001.fastq
lane7-s0009-index--ATTACTCG-CCTATCCT-195_S9_L007_R1_001.fastq
lane7-s0010-index--ATTACTCG-GGCTCTGA-106_S10_L007_R1_001.fastq
lane7-s0011-index--ATTACTCG-AGGCGAAG-197_S11_L007_R1_001.fastq
lane7-s0096-index--AGCGATAG-CAGGACGT-287_S96_L007_R1_001.fastq
我创建了一个名为 RENAMING_parse_data.sh 的文件,它引用了 RENAMING_parse_data.pl
所以理论上,这个想法是解析数据以找到位于名称中间的样本#,并获取该唯一 ID 并重命名它。但我认为它甚至不会进入 IF 循环。 有什么想法吗?
这里是调用 perl scipt 的 .sh 文件
#!/bin/bash
#first part is the program
#second is the directory path
#third and fourth times are the names of the output files
#./parse_data.pl /ACTF/Course/PATHTDIRECTORY Tabsummary.txt Strucsummary.txt
#WHERE ./parse_data.pl =name of the program
#WHERE /ACTF/Course/PATHTODIRECTORY = directory path were your field are saved AND is referred to as $dir_in = $ARGV[0] in the perl script;
#new files you recreating with the extracted data AND is refered to as $dir_in = $ARGV[1];
./RENAMING_parse_data.pl ./Test/ FishList.txt
这里是 PERL 脚本:
#!/usr/bin/perl
print (":)\n");
#Proesessing files in a directory
$dir_in = $ARGV[0];
$indv_list = $ARGV[1];
#open directory to acess those files, the folder where you have the files
opendir(DIR, $dir_in) || die ("Cannot open $dir_in");
@files = readdir(DIR);
#set all variables = 0 to void chaos
$j=0;
#open output header line for output file and print header line for tab delimited file
open(OUTFILETAB, ">", $indv_list);
print(OUTFILETAB "\t Fish ID", "\t");
#open each file
foreach (@files)
#re start all arrays to void chaos
print("in loop [$j]");
@acc_ID=();
#find FISH name
#EXAMPLE FISH NAMES: (lenth of fishname varies)
#lane8-s251-index--TCCGGAGA-TAATCTTA-14_S251_L008_R1_001.fastq.gz
#lane7-s0096-index--AGCGATAG-CAGGACGT-287_S96_L007_R1_001.final.fastq
#NOTE: what is in btween () is the ID that is printed NOTE that value can change from 2 -3 depending on Sample #
#Trials:
#lane[0-9]1-[a-z]1[0-9]4-index--[A-Z]8[A-Z]8-([0-9]3)[a-z]1[0-9]2_[A-Z]1[0-9]3_[a-z]1[0-9]1_[0-9]3.fastq
#lane[0-9]1-[a-z]1[0-9]4-index--[A-Z]8[A-Z]8-([0-9]3)*.fastq
#lane*([0-9]3)*.fastq
#lane.*-([0-9]2)_.*.fastq
#lane.*-([0-9]2)_*.fastq
#lane[0-9]1-[a-z]1[0-9]3-index--[A-Z]8[A-Z]8-([0-9]2)_[A-Z]1[0-9]3_L008_R1_001.fastq
$string_FISH = @files;
if ($string_FISH =~ /^lane[0-9]1-[a-z]1[0-9]3-index--[A-Z]8[A-Z]8-([0-9]2)_[A-Z]1[0-9]3_L008_R1_001.fastq/)
$FISH_ID =$1;
@acc_ID[$j] = $FISH_ID;
#print ("FISH. = |$FISH_ID[$j]| \n");
rename($string_FISH, "FISH. = |$FISH_ID[$j]|");
#print ($acc_ID[$j], "\n");
print(OUTFILETAB "FISH. = |$FISH_ID[$j]| \n");
$j= $j+1;
理想的最终结果
所以最后我希望它取文件名,找到唯一标识符并重命名它
来自:
lane8-s244-index--ATTACTCG-TATAGCCT-01_S244_L008_R1_001.fastq
lane7-s0007-index--ATTACTCG-TATAGCCT-193_S7_L007_R1_001.fastq
到:
Fish.01.fastq
Fish.193.fastq
非常感谢任何关于解决此问题或需要完全更改的想法或建议。
【问题讨论】:
所以您只想将它们都称为Fish.NN.fastq
,而不管其原始名称中的所有其他细节? (其中NN
代表01
、193
等)
你不需要重新发明一个***,有一个命令rename,请看examples。
或者perl自带的rename(1)
的版本;有时称为prename
以避免与Polar 提出的(能力较差的)util-linux 冲突:systutorials.com/docs/linux/man/1-prename
我正在使用重命名命令。问题是这些数字都是不同的且不连续的。是的,我想要的只是 Fish.NN.fastq 我不需要所有其他信息。
【参考方案1】:
在 Perl 解决方案的核心,您可以使用
s/^.*-(\d+)_[^-]+(?=\.fastq\z)/Fish.$1/sa
例如,
$ ls -1 *.fastq
lane8-s244-index--ATTACTCG-TATAGCCT-01_S244_L008_R1_001.fastq
lane8-s245-index--ATTACTCG-ATAGAGGC-02_S245_L008_R1_001.fastq
lane8-s246-index--TCCGGAGA-TATAGCCT-09_S246_L008_R1_001.fastq
lane8-s247-index--TCCGGAGA-ATAGAGGC-10_S247_L008_R1_001.fastq
lane8-s248-index--TCCGGAGA-CCTATCCT-11_S248_L008_R1_001.fastq
lane8-s249-index--TCCGGAGA-GGCTCTGA-12_S249_L008_R1_001.fastq
$ rename 's/^.*-(\d+)_[^-]+(?=\.fastq\z)/Fish.$1/sa' *.fastq
$ ls -1 *.fastq
Fish.01.fastq
Fish.02.fastq
Fish.09.fastq
Fish.10.fastq
Fish.11.fastq
Fish.12.fastq
(有两个类似的工具名为rename
。这个也称为prename
。)
自己实现非常简单:
#!/usr/bin/perl
use strict;
use warnings;
my $errors = 0;
for (@ARGV)
my $old = $_;
s/^.*-(\d+)_[^-]+(?=\.fastq\z)/Fish.$1/sa;
my $new = $_;
next if $new eq $old;
if ( -e $new )
warn( "Can't rename \"$old\" to \"$new\": Already exists\n" );
++$errors;
elsif ( !rename( $old, $new ) )
warn( "Can't rename \"$old\" to \"$new\": $!\n" );
++$errors;
exit( !!$errors );
提供要重命名的文件作为参数(例如,使用 shell 中的 *.fastq
)。
$ ls -1 *.fastq
lane8-s244-index--ATTACTCG-TATAGCCT-01_S244_L008_R1_001.fastq
lane8-s245-index--ATTACTCG-ATAGAGGC-02_S245_L008_R1_001.fastq
lane8-s246-index--TCCGGAGA-TATAGCCT-09_S246_L008_R1_001.fastq
lane8-s247-index--TCCGGAGA-ATAGAGGC-10_S247_L008_R1_001.fastq
lane8-s248-index--TCCGGAGA-CCTATCCT-11_S248_L008_R1_001.fastq
lane8-s249-index--TCCGGAGA-GGCTCTGA-12_S249_L008_R1_001.fastq
$ ./a *.fastq
$ ls -1 *.fastq
Fish.01.fastq
Fish.02.fastq
Fish.09.fastq
Fish.10.fastq
Fish.11.fastq
Fish.12.fastq
存在性检查 (-e
) 是为了防止意外地将一堆文件重命名为相同的名称,从而导致除了一个文件之外的所有文件都丢失。
以上是我经常使用的单线模式的清理版本。
dir /b ... | perl -nle"$o=$_; s/.../.../; $n=$_; rename$o,$n if!-e$n"
改编为sh
:
\ls ... | perl -nle'$o=$_; s/.../.../; $n=$_; rename$o,$n if!-e$n'
【讨论】:
我会试试这个:) 没用 :( Tested. Works fine. 我认为我做错了。我是否需要在 .sh 中列出要重命名的所有文件?然后全部列出我需要重命名的内容? 如所写,您需要“提供要重命名的文件作为参数(例如,使用 shell 中的*.fastq
)。”请参阅自您之前发表评论以来我提供的三个示例。以上是关于解析唯一数据和重命名文件的主要内容,如果未能解决你的问题,请参考以下文章