2017-07-21 158 views
-1
my $file = '/var/tmp/temp_data.txt';  ##################### File for reading 
    open(FILE, '<:encoding(UTF-8)', $file) || die("Unable to open file"); 
    my @fieldss = <FILE>; 
    close(FILE); 
    chomp @fieldss; 

    my @fields = split(':', @fieldss);####################### Splitting the lines in file ############## 
####################################### Dereference ############################ 
    my $names = $fields[0]; 
    my $rate = $fields[1]; 
    my $no_of_days = $fields[2]; 
    my $total_salary = $fields[3]; 
    my $total = $fields[4]; 
    my $basic = $fields[5]; 
    my $da = $fields[6]; 
    my $hra = $fields[7]; 
    my $ot_hallowance = $fields[8]; 
    my $gross = $fields[9]; 
    my $epf = $fields[10]; 
    my $nett = $fields[11]; 

    print "$names\n $rate\n"; 

     foreach $names (@fields) { 
       my $dbh = "DBI:$platform:$database:$host:$port"; 
       my $connect = DBI->connect($dbh, $user, $pw) || die $DBI::errstr; 
       $query = "SELECT * FROM salary WHERE name IN('sssss', 'ffffff', 'dddddd', 'ddededed', 'garaead', 'adgfdfg', 'gadfredg')"; 
       my $sth = $connect->prepare($query); 
       $sth->execute() || die $DBI::errstr; 

       my @data2; 
       while (@data2 = $sth->fetchrow_array()) { 
        my $name = $data2[0]; 
        my $email = $data2[1]; 

         if ($names eq $name) { ######################### Comparing names in file and database ######################## 

上面的代碼是讀取文本文件和數據使用split函數進行拆分。我的問題是我在閱讀和分割文件時犯了錯誤。我在運行代碼時遇到了504錯誤,我認爲這是因爲在文本文件中爲每一行調用數據庫。謝謝你的幫助。將文本文件讀入perl中的陣列

+1

請勿使用裸號文件句柄。現在不是1999年了。 – melpomene

+2

'split(':',@fieldss)'不會分割文件中的行。 'split'只接受一個字符串,而不是一個數組。你期望這個做什麼? – melpomene

+0

你的網絡服務器的錯誤日誌裏有什麼? – melpomene

回答

2

這將有助於查看輸入文件中的數據是什麼樣子。但是在你的代碼中肯定會有一些奇怪的事情發生。主要的問題似乎是這一行:

my @fields = split(':', @fieldss); 

split()需要兩個標量參數 - 一個正則表達式拆就和一個字符串分割。因此,它在標量上下文中計算@fieldss並獲取數組中元素的數量。當然,這將是一個整數,不包含冒號。這導致@fields包含單個元素,這是@fieldss中元素的數量。這個例子說明:

use Data::Dumper; 

my @arr = qw[1:foo 2:bar 3:baz]; 

my @arr2 = split /:/, @arr; 

say Dumper @arr2; 

我得到的輸出是:

$VAR1 = '3'; 

你的代碼來設置@fields或許應該更多這樣的:

my $file = '/var/tmp/temp_data.txt'; 
open(my $fh, '<:encoding(UTF-8)', $file) 
    # Note: Added filename and error code to output. 
    || die("Unable to open $file: $!"); 

my @fields; 
while (<$fh>) { 
    chomp; 
    push @fields, split /:/; 
} 
close $fh; 

我沒有看過在你的代碼的其餘部分詳細介紹,但它肯定會提出一些問題。您的陣列到各個變量的複製可能是毫無意義的,但可以在單個語句來實現:

my ($names, $rate, $no_of_days, $total_salary, $total, 
    $basic, $da, $hra, $ot_hallowance, $gross, $epf, 
    $nett) = @fields; 

但你遍歷@fields,看似假設每個元素的名稱。也許你需要更詳細地解釋你在做什麼。

但是,這些都不能解釋您獲得的504狀態碼。您提到您正在爲文本文件中的每一行運行數據庫查詢。在你的循環的每次迭代中,你確實是一樣的查詢 - 這似乎是非常浪費的(只運行一次並將結果存儲在一個變量中),但是,因爲我們已經確定@fields只能做到包含一個元素,你的循環只運行一次,你只能查詢一次數據庫。

嚴格來說,這可能不是您的問題的答案。但是你的問題留下了太多無法解釋的事情,無法回答。希望這會給你一些洞見,說明你如何能夠改善你的計劃,以至於我們可以開始解決目前隱藏的真實問題。

更新:我剛剛意識到輸入文件的結構是什麼。你可能想把它讀成使用這樣的代碼散列的數組:

my $file = '/var/tmp/temp_data.txt'; 
open(my $fh, '<:encoding(UTF-8)', $file) 
    # Note: Added filename and error code to output. 
    || die("Unable to open $file: $!"); 

my @records; # Terrible variable name! 
my @cols = qw[names rate no_of_days total_salary total basic da 
       hra ot_hallowance gross epf nett]; 

while (<$fh>) { 
    chomp; 
    my %rec; 
    @rec{@cols} = split /:/; 
    push @records, \%rec; 
} 
+0

'J. XXXXXX:17000:30:17000:11900:9520:2380:3400:1700:17000:1428:15572: S. XXXXX:15000:0:0:0:0:0:0:0:0:0:0 : K. XXXXXX:12000:30:12000:8400:6720:1680:2400:1200:12000:1008:10992: A. XXXXX:9000:27:8100:5670:4536:1134:1620:810:8100 :680:7420: S. XXXXX:9000:30:9000:6300:5040:1260:1800:900:9000:756:8244: I. XXXXX:9000:26:7800:5460:4368:1092:1560 :780:7800:655:7145: J. XXXXX:8000:29:7733:5413:4330:1083:1547:773:7733:650:7083: X. XXXXX:8000:26:6933:4853:3882 :971:1387:693:6933:582:6351:' 我的輸入文件 –

+0

@prakashg:在像這樣的評論中轉儲數據根本沒有幫助。請編輯您的問題以添加此內容。你也可以藉此機會更多地解釋你在做什麼。 –

0

我甚至不知道你的文件的樣子。但是在將蛋白質數據庫(PDB)文件讀入數組之前,我已經完成了這種類型的事情,然後將它們按照與我的空白分開的列分開。我不能保證我的代碼可以工作,因爲我甚至沒有你的文件,但無論如何,問題是你如何閱讀文件,然後將其分成列是問題,是的...

您的分割不起作用,因爲您不分割,但是您的分隔列可能是逗號或至少一個空格。但是我從來沒有在文件中看到像你說的冒號分隔的列。此外,是的,你可以將文件讀入數組中,但要將所有列作爲每行的標量,我認爲您需要在循環中繼續執行此操作,否則每個列的值都不會擴展所有的文件。好的,你真的分裂了冒號。我對這個麻煩感到抱歉。請原諒我。

#!/usr/bin/env perl 
# Program Description: _________ 
use strict; 
use warnings; 
use feature 'say'; # say is like print, but you don't need to type \n. 

my $file = '/var/tmp/temp_data.txt';  ##################### File for reading 
my $filehandle; # Just like your bareword filehandle FILE. 
my @fields =(); # My use of fields is the same as yours. 
open($filehandle, '<', $file) or die "Could not open file $_ because $!"; 

my @All_Lines = <$filehandle>; # This is just everything in the file ... all lines. 
my $line; # Our current line which will be useful for the split. 
close $filehandle; 

# We will declare all of our variables outside of a loop 
# That we split all the columns of the file on on colon. 
# ... declaring our variables now so they don't get locked in our loop. 
my $names; 
my $rate; 
my $no_of_days; 
my $total_salary; 
my $total; 
my $basic; 
my $da; 
my $hra; 
my $ot_hallowance; 
my $gross; 
my $epf; 
my $nett; 

# Iterating over ever line of the file in a foreach loop. 
foreach $line (@All_Lines) 
{ 

    @fields = split(':', $line); # splitting on a colon. 

$names = $fields[0]; 
$rate = $fields[1]; 
$no_of_days = $fields[2]; 
$total_salary = $fields[3]; 
$total = $fields[4]; 
$basic = $fields[5]; 
$da = $fields[6]; 
$hra = $fields[7]; 
$ot_hallowance = $fields[8]; 
$gross = $fields[9]; 
$epf = $fields[10]; 
$nett = $fields[11]; 

say "$names $rate"; 

# Then I'm pretty sure that I can dump the rest of your code here 
# And you should because @fields is now within this foreach loop. It doesn't exist anywhere else. 
# I'm pretty sure I'm justified in removing your foreach loop here 
# Because in mine, the column of names will be read and operated on line by line. 
# Also, your goal was to iterate over $names with a foreach loop 
# which I'm doing right now, but where are you operating on it? 

     # Perhaps you should declare these variables with "my" before we start looping through all the lines of the file one line at a time. 
     # But I think you will be okay having them here. 
     my $dbh = "DBI:$platform:$database:$host:$port"; 
     my $connect = DBI->connect($dbh, $user, $pw) || die $DBI::errstr; 
     # You didn't declare query with "my $query". I think you should, especially since I classically enabled "use strict". 
     $query = "SELECT * FROM salary WHERE name IN('sssss', 'ffffff', 'dddddd', 'ddededed', 'garaead', 'adgfdfg', 'gadfredg')"; 
     my $sth = $connect->prepare($query); 
     $sth->execute() || die $DBI::errstr; 

     my @data2; 
     # So @data2 gets formed when you start the while loop, right? 
     while (@data2 = $sth->fetchrow_array()) 
       { 
        my $name = $data2[0]; 
        my $email = $data2[1]; 

         if ($names eq $name) 
         { 
           ######################### Comparing names in file and database ######################## 
         } # This bracket ends your if conditional 
       } # This bracket ends your while loop. 

} # This bracket ends my foreach loop that you want to stay within. 

# Note: Commenting where brackets begin and end can be really useful when you are trying to stay within a loop. 

注:I測試基於上的文件 一個或多個空白分割其是PDB文件看起來像這樣由一個或多個白空間分離,並且PDB文件的每一列可以被逐行隔離,所以我很肯定這會在你的文件上起作用。

ATOM  38 CB PHE A 7  15.240 41.685 54.772 1.00 10.03   C 
ATOM  39 CG PHE A 7  15.740 42.936 54.063 1.00 12.39   C 
ATOM  40 CD1 PHE A 7  15.096 44.166 54.328 1.00 11.59   C 
ATOM  41 CD2 PHE A 7  16.851 42.864 53.189 1.00 10.59   C 
ATOM  42 CE1 PHE A 7  15.540 45.310 53.626 1.00 12.79   C 
ATOM  43 CE2 PHE A 7  17.329 44.058 52.581 1.00 13.07   C 
ATOM  44 CZ PHE A 7  16.651 45.259 52.776 1.00 12.33   C 
ATOM 156 CG GLU A 20  14.635 48.596 50.249 1.00 9.28   C 
ATOM 157 CD GLU A 20  15.173 49.229 51.481 1.00 10.96   C 
ATOM 158 OE1 GLU A 20  15.790 50.279 51.395 1.00 11.04   O 
ATOM 159 OE2 GLU A 20  14.851 48.625 52.550 1.00 13.31   O 

現在,我通常會在程序的後面關閉一個文件的方式,但是您是對的。即使在關閉文件後,也可以將其保存到數組中並逐行操作該數組。

+0

*但是我從來沒有見過文件中的列被冒號分隔,就像你說的一樣*你從來沒有看過Linux系統上的'/ etc/passwd'文件嗎? –

+0

什麼是「診斷」模塊? CPAN上沒有稱爲「診斷」的模塊。當然有[diagnostics](https://metacpan.org/pod/distribution/perl/lib/diagnostics.pm),但是沒有人需要從CPAN安裝它,因爲它是標準Perl發行版的一部分,二十多年。 –

+0

*你的分割不工作,因爲你不分裂,但是你的列被分開*不。他的分割沒有工作,因爲他試圖分割一個數組。 –