2015-12-04 128 views
1

我是新來的perl,並且在使用Cartesian產品時遇到了麻煩。我已經找到了模塊Set :: CrossProd和Math :: Cartesian :: Product,但我可以讓他們爲我的用法工作,因爲我需要生成一個數組。Perl獲取適當的陣列陣列

我確實想要做的是從一個基因序列(長度可變,取決於輸入),讓我們使用例如ARDN,我想要所有可能的輸出序列。 我說所有的,因爲事實上,R表示A或G,d是指A,G或T和N表示A,T,C,或G.

因此,我所做,是具有陣列的一個散列不同的可能字母,然後用循環將輸入序列轉換爲數組數組。 所以在我們的例子中,我應該得到:

@AoA = (
["A"], 
["A", "G"], 
["A", "G", "T"], 
["A", "T", "C", "G"], 
); 

然而,似乎是我得到的標量的數組,因爲當我打印出來,我所顯示的字母。

我的代碼:

my %alphabet = (     #not complete for simplification 
    A => ["A"], 
    D => ["A" , "G", "T"], 
    N => ["A", "T", "C", "G"], 
); 

my @test = (
["A"], 
["A" , "G", "T"], 
["A", "T", "C", "G"], 
); 


my $seq = <STDIN>; 
chomp $seq; 
$seq =~ s// /g; 
my @sequence = split(" ", $seq, length($seq)); 

my @AoA; 
for (my $i = 0; $i < $#sequence; $i++) { 
    push (@AoA, @{$alphabet{$sequence[$i]}}); 
}; 

print "@test"; 
print "@AoA"; 

輸出:

ARDN 
ARRAY(0x84ea30) ARRAY(0x867780) ARRAY(0x8677f8) 
A A G A G T A T C G 

我做了什麼錯? 謝謝

+0

當你想看到任何變量的詳細內容:use Data :: Dumper;打印Dumper($ whatever_variable); – jcaron

+0

你可以簡化你的分割爲'my @sequence = split //,$ seq;' – jcaron

+1

你的for循環是不正確的。 '$#array'給你最後一個索引,而不是數組的大小,所以你應該使用'<='。但更好的是,使用'for $ s(@sequence)'代替循環中的'@ s'中的每個'@ sequence'成員 – jcaron

回答

3

在perl中,數組不能正確地包含另一個數組。您的push將第二個列表的元素添加到數組中。您應該推送對數組的引用(然後調整剩餘的代碼以期望引用)。

push (@AoA, \@{$alphabet{$sequence[$i]}}); 
+0

這個工作,現在我可以做笛卡爾產品!非常感謝 ! –

+0

很高興聽到它。由於您的問題已解決,請點擊左側的大號複選標記以「接受」我的答案。 – alexis

+1

請注意,如果%字母的內容沒有改變,也不會通過AoA改變它們,你可以直接添加一個參考:'push @ AoA,$ alphabet {$ sequence [$ i]}' 。上面的代碼將創建數組的副本,而不是指向它。 – jcaron

0

這看起來像一個完美使用案例map,當你需要改變的事情的清單到的東西一個新的列表,這是偉大。大部分代碼可以簡化爲下面的例子,在我看來,它更加優雅和清晰。

my $seq = <STDIN>; 
chomp($seq); 
my @AoA = map { $alphabet{uc($_)} } split(//, $seq);