2009-11-01 21 views
16

以下のコードは単なるカウント値を得るには多すぎるようです。 プレーンDBIを使用して1つのCOUNT値をフェッチする方法が推奨されていますか?DBIを使用してデータベースから単一のカウント値をフェッチする方法はありますか?

sub get_count { 
    my $sth = $dbh->prepare("SELECT COUNT(*) FROM table WHERE..."); 
    $sth->execute(@params); 
    my $($count) = $sth->fetchrow_array; 
    $sth->finish; 

    return $count; 
} 

これは短いですが、まだ2つのステートメントがあります。

sub get_count_2 { 
    my $ar = $dbh->selectall_arrayref("SELECT ...", undef, @params) 
    return $ar->[0][0]; 
} 
+1

これは少し主観的です。あなたの長い例はより読みやすいと言う人もいます。私たちはPerlゴルフをしていますか? – pavium

+4

あなたの声明はいくつですか? –

+0

私は自分のコードで多くのそのような呼び出しを持っているので、私はSQL文と@paramsを取得し、カウントを返すサブを持っています。 DBIで組み込みの文があれば、余分なサブは必要ありません。私はそれが一般的な使用事例だと思うし、そのような声明があったかどうか、私はそれを逃したか、DBIにそのような声明がないかどうか疑問に思っていた。 – szabgab

答えて

33

$count = $dbh->selectrow_array('SELECT count(*) FROM table WHERE...', undef, @params); 
+1

それは私の解決策でもあります。 – MarkR

+1

それは私が探していたものです。ありがとう! – szabgab

+0

docはあなたがリストコンテキストでなければならないと言っています。個人的に私は '(my $ count)= $ dbh-> selectrow_array( 'SELECT count(*)FROM table WHERE ...'、undef、@params); ' –

3

私はPerlを知らないが、それは構文が論理的であるかどう私はこれがあなたの第二の例に基づいて動作すると思うだろう:余分な変数を1行で行うのに十分簡単

sub get_count { 
    return $dbh->selectall_arrayref("SELECT ...", undef, @params)->[0][0]; 
} 
+2

Perlを知らない人には良い推測です。 :) – friedo

+0

niceですが、$ dbh-> selectall_arrayref( "SELECT ..."、undef、@params) - > [0] [0]です。呼び出しはベクトルではなく行列を返します。 (私のオリジナルの例では同じミスがありましたが、あなたのコメント以来修正しました) – szabgab

+0

OK、それを修正しました。 –

1

私はおそらくこれを自分でしないだろうが、あなたは常にそれあなたが使用しているDBHオブジェクトの新しいトップレベルの機能を作ることができます:

警告:テストされていないコードが続きます!

sub DBD::SQLite::db::count 
{ 
    my($dbh, $table, $where) = @_; 

    my($stmt) = "SELECT COUNT(*) FROM $table"; 
    $stmt .= " WHERE $where" if $where; 

    my($count) = $dbh->selectrow_array($stmt); 

    return $count; 

} 

し、このようにそれを呼び出す:私はあなたの確信しているのに、あなたはありません名前空間を汚染するだけでなく

my($cnt) = $dbh->count('Employee', 'year_hired < 2000'); 

、あなたは、あなたが使用するすべてのDBドライバのためにこれを書くこともあるだろう特定のDBHオブジェクトのためにこれを自動構成するコードをいくつか構築し、評価することができる何かを働かせることができます。

+1

他の人の名前空間を汚染し、使用するすべてのDBDについて書き換える必要があるのとは別に、提示されている解決策では、値を補間する必要がありますプレースホルダ( 'year_hired <?')を失う代わりにSQL文字列に変換するため、SQLインジェクション攻撃に対する可能な限りの保護を得ることができなくなります。 –

+0

良い点;しかし、このことは、OPのコメント「DBIのそれについての組み込み文があれば」に反応していました。 –

関連する問題