2016-02-17 54 views
4

我有一個涉及複雜數據結構的Perl相關問題。我在Linux(Centos v5)服務器上運行Perl 5.8.8版本,託管Apache。我在詢問MS-SQL數據庫。我正在使用「DBI」Perl模塊。通過Perl中的哈希引用數組獲取切片

我有一個SQL查詢的結果表,編碼爲哈希引用數組的引用。因此,表中的每一行都是一個數組元素,其中包含使用DBI模塊的「fetchrow_hashref」命令獲取的散列引用。每個散列的鍵對應於列標題和與該列標題下的表中的特定單元格對應的值。我想要做的是獲取列數據的數組。似乎在DBI文檔中描述了有關如何獲取列數據的一些方法,但對我而言它們有點不透明,並且通常瞭解如何通過散列引用數組獲得切片作爲練習瞭解perl引用/解引用如何工作。

所以,基本上,考慮到本:

my %datarow1 = {"firstname"=> "dave", "bar"=>"smith"}; 
my %datarow2 = {"firstname"=> "john", "bar"=>"doe"}; 
my %datarow3 = {"firstname"=> "kim", "bar"=>"kardashian"}; 

引用這樣的:

我如何獲得這個數組?:

("dave", "john", "kim") 

我已經試過這樣:

my @[email protected]$rowsref->[0]{"firstname"} 

但這隻讓我第一個單元格列(即包含一個元素「dave」的數組)。 必須有一個優雅的方式來做到這一點 - 如果你的perl guru可以幫助我,我會非常感激。

感謝

CJ

+0

'perl' 5.8.8已經很老了。您可能需要考慮更新它。 – Sobrique

+0

謝謝 - 我很想更新它,但這不是我的電話! –

回答

6

有幾件事情開始:

這不是你如何定義一個哈希:

my %datarow1 = {"firstname"=> "dave", "bar"=>"smith"}; 

這行代碼將一個散列引用賦值給一個散列,這會產生一個像這個:

('HASH(0x7f4ef0545e18)' => undef) 

可能不是你想要的。

要定義你的散列正確使用括號代替花括號:

my %datarow1 = ("firstname"=> "dave", "bar"=>"smith"); 

始終啓用嚴格模式和警告:

use strict; 
use warnings; 

這本來是可以趕上的分配基準的錯誤散列。

-

現在,真正的問題是「我如何提取從陣列中的哈希舉行引用一個特定的鑰匙嗎?」

,答案是完全相同的方式一樣,如果哈希引用不是在一個陣列:

my $h_ref = { a => b }; 
# get key 'a' 
my $a = $h_ref->{a}; 

唯一不同的是,你需要一個數組應用此操作。施加動作在陣列是map內置的宗旨:

use strict; 
use warnings; 

my %datarow1 = ("firstname"=> "dave", "bar"=>"smith"); 
my %datarow2 = ("firstname"=> "john", "bar"=>"doe"); 
my %datarow3 = ("firstname"=> "kim", "bar"=>"kardashian"); 

my @rows = (\%datarow1, \%datarow2, \%datarow3); 
my $rowsref=\@rows; 
my @firstnames = map { $_->{firstname} } @$rowsref; 
# dave john kim 
+0

謝謝 - 工作過! (順便說一下,我總是使用嚴格和警告, - 我發佈的代碼更像是一個簡單的示例代碼片段,而不是實際的腳本。我發佈時很急,所以我忘記了支架慣例! ) –

3

如果你使用use strict; use warnings;你會得到:

參考找到預期的 「腳本」, 「線」

偶數大小的列表

你想填充一個散列,使用:

my %datarow1 = ("firstname"=> "dave", "bar"=>"smith"); 

注意括號,而不是大括號

然後,打印名字,用途:

my @columndata = map {$_->{"firstname"}} @$rowsref; 
say Dumper\@columndata; 
0

[編輯:已經回答了,但我ading這爲TIMTOWDI -ness]

隨着perl5.22.0你也可以這樣做:

use experimental 'refaliasing'; 

for \my %hash (\%datarow2, \%datarow1, \%datarow3) { 
     say $hash{"firstname"} ; 
}