Perl解析Phobius输出文件时实现每个FT行前置对应Uniprot ID的问题咨询
修复Perl脚本实现每个FT行前添加对应Uniprot ID
你的问题很明确:Phobius输出里每个Uniprot ID对应的多条FT行,只有第一条带ID,后面的都缺失了。咱们来改改这个脚本,让每个FT行都能带上对应的ID。
先看你原来的代码问题出在哪:你在匹配到ID行的时候直接把ID打印到文件里了,但只有第一个FT行会跟着这个ID,后面的FT行因为没有触发ID的打印逻辑,就直接输出了。正确的思路应该是保存当前ID,然后每遇到FT行,就把保存的ID和FT内容一起输出,而不是在ID行的时候提前打印。
原代码问题点
open (MYFILE, "result_phobius.txt" )||warn "Couldn't open file because $!"; #指定输入文件名 open (FILE, ">output.txt"); #指定输出文件名 while (<MYFILE>) { if ($_=~/^ID (\S+?)\s/) #匹配以ID开头的行,提取Uniprot ID { $id=$1; chomp ($id); print FILE "$id\t"; #在输出文件中打印Uniprot ID } if ($_=~/^FT /) { print FILE "$_"; #打印FT开头的行 } }
修改后的代码
# 打开输入文件,用三参数open更安全 open(my $in_fh, '<', 'result_phobius.txt') or die "Couldn't open input file: $!"; # 打开输出文件 open(my $out_fh, '>', 'output.txt') or die "Couldn't open output file: $!"; my $current_id; # 保存当前的Uniprot ID while (my $line = <$in_fh>) { chomp $line; # 先去掉每行的换行符,方便后续处理 if ($line =~ /^ID (\S+)/) { # 匹配ID行,提取ID $current_id = $1; } elsif ($line =~ /^FT /) { # 匹配FT行 # 只有当前ID存在时才输出,避免空ID的情况 if (defined $current_id) { print $out_fh "$current_id $line\n"; } } # 跳过分隔线和空行,不需要处理 } # 关闭文件句柄 close $in_fh; close $out_fh;
修改说明
- 改用三参数open:比你原来的两参数open更安全,避免文件名包含特殊字符时出问题,同时用词法文件句柄(
$in_fh/$out_fh)代替全局句柄,更规范。 - 保存当前ID而非提前打印:遇到ID行时,只把ID存在
$current_id变量里,不直接输出到文件。 - 处理FT行时拼接ID:每遇到FT行,就把之前保存的
$current_id和FT内容拼接后输出,这样每个FT行都会带上对应的ID。 - 添加空ID判断:防止文件开头有FT行但还没匹配到ID的情况,避免输出空ID。
- 统一处理换行符:先chomp掉原行的换行,输出时自己加
\n,保证换行一致。
验证效果
修改后的脚本运行后,会输出你期望的格式:
sp|Q92673|1-2157 FT SIGNAL 1 28
sp|Q92673|1-2157 FT DOMAIN 1 11 N-REGION.
sp|Q92673|1-2157 FT DOMAIN 12 22 H-REGION.
...
tr|D3DPA4|1-145 FT TRANSMEM 120 144
tr|D3DPA4|1-145 FT DOMAIN 145 145 NON CYTOPLASMIC.
内容的提问来源于stack exchange,提问作者Kay
相关产品推荐
相关产品推荐

