Click here to view and discuss this page in DocCommentXchange. In the future, you will be sent there automatically.

SQL Anywhere 11.0.1 (日本語) » SQL Anywhere サーバ - SQL の使用法 » データのクエリと変更 » クエリ結果の要約、グループ化、ソート » 集合関数を使用したクエリ結果の要約

 

集合関数を使用できる場所

前述の例のように、集合関数は select リストで使用するか、GROUP BY 句を含む SELECT 文の HAVING 句で使用します。HAVING 句:データ・グループの選択を参照してください。

WHERE 句や JOIN 条件の中では、集合関数は使用できません。しかし、select リストの集合関数による SELECT 文には、多くの場合、その集合関数が適用されるローを制限する WHERE 句があります。

SELECT 文に WHERE 句が入っているが GROUP BY 句は入っていない場合、集合関数は、WHERE 句が指定するローのサブセットに対して単一の値を生成します。

GROUP BY 句がない SELECT 文で集合関数を使用すると、必ず単一の値が生成されます。これは、その関数がテーブル内のすべてのローに作用するか、WHERE 句が定義したローのサブセットに作用するかに関係なく、生成されます。

同一の select リストで 2 つ以上の集合関数を使用でき、単一の SELECT 文で 2 つ以上のスカラ集合関数を作成できます。

集合関数と外部参照

SQL Anywhere は、サブクエリでの集合関数の使用法を明確に規定した SQL/2003 標準に準拠しています。この変更は、Adaptive Server Anywhere の以前のバージョン用に記述された文の動作に影響を与えます。以前は正しかったクエリでエラー・メッセージが生成され、結果セットが変わる可能性があります。

集合関数がサブクエリに使用され、集合関数の参照先カラムが外部参照の場合は、集合関数全体が外部参照として扱われるようになりました。これは、集合関数がサブクエリ内ではなく外部ブロック内で計算されるようになり、サブクエリ内の定数となることを意味しています。

サブクエリに含まれる外部参照の集合関数の使用には、次の制限が適用されます。

  • 外部参照の集合関数を指定できるのは、SELECT リストまたは HAVING 句にあるサブクエリの中だけです。また、これらの句は、外部ブロックの隣になくてはなりません。

  • 外部参照の集合関数に指定できるのは、1 つの外部カラム参照だけです。

  • ローカル・カラム参照と外部カラム参照を、同じ集合関数に混在させることはできません。

新しい標準に関連する問題は、ローカル参照しか含まないように集合関数を書き換えると回避することができます。たとえば、サブクエリ (SELECT MAX(S.y + R.y) FROM S) がローカル・カラム参照 (S.y) と外部カラム参照 (R.y) の両方で構成されていると、不正になります。このサブクエリは (SELECT MAX(S.y) + R.y FROM S) に書き換えることができます。書き換えると、集合関数はローカル・カラム参照だけを持つことになります。外部参照の集合関数が SELECT や HAVING 以外の句に指定されている場合にも、同様の書き換えを使用できます。

次のクエリの場合、Adaptive Server Anywhere バージョン 7 では次に示す結果が生成されました。

SELECT Name, 
      ( SELECT SUM( p.Quantity )
           FROM SalesOrderItems )
   FROM Products p;
Name SUM(p.Quantity)
Tee Shirt 30,716
Tee Shirt 59,238

新しいバージョンで同じクエリを実行すると、「SQL Anywhere エラー -149: 'name' に対する関数またはカラムの参照も GROUP BY 句に記述する必要があります。」というエラー・メッセージが生成されます。この文が有効ではなくなったのは、外部参照の集合関数 sum(p.Quantity) が外部ブロック内で計算されるようになったためです。最新のバージョンでは、このクエリはセマンティック上は次のクエリと同じです (Z が結果セットに表示されないことを除く)。

SELECT Name,
       SUM( p.Quantity ) AS Z,
       ( SELECT Z 
            FROM SalesOrderItems )
   FROM Products p;

外部ブロックが集合関数を計算するようになったため、外部ブロックはグループ化したクエリとして扱われます。また、カラム名を SELECT リストに表示するには、GROUP BY 句に指定する必要があります。