第1篇の博文のmysql表の接続クエリーと行列の置換の問題


ちょうど卒业して1ヶ月働いて、小さい会社に入って、会社のコードを见る过程の中でいつもいくつかN长いsql文を见て、にらんで半日见ても分からないで、もともとデータベースに接触するのは少なくて、その上数年も触っていないで、そこで、インターネットで调べて、もとは表の接続の検索と行列の置換についてです.
そこで、csdnに助けを求める投稿を出しました.そして問題は順調に解決して、次に簡単にまとめて、自分が後で忘れなければならないことを便利にして、また振り返ることができます.
2つのテーブル:
表1:業績表
+-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
表2:部門表
+--------------+|dep|dname|+----------------------------+|1|一部||2|二部||3|三部||4|国際部|+--------------++
次の結果が得られます.
dep dname 1月2月3月---------------------------------------------01国内業務一部10 null null 02国内業務2部10 8 null 03国内業務3部null 5 8 04国際業務部null null 9
問題が解決して、私の最大の感じは、sqlの実行順序を理解することが重要で、私が長い間データベースに触ったことがないかもしれませんが、以前データベースを勉強したとき、このような知識点が最も基礎的なものだったようです.ああ、意外にも私の印象があります.ははは.私の思考過程を具体的に説明します.
最初のステップ:まず、2つのテーブルがクエリーに接続されるに違いありません.そのため、接続クエリーの結果は次のとおりです.
sql:select b.dep,b.dname,a.mon,a.yj from table1 a,table2 b where a.dep = b.dep;
 
ステップ2:初歩的な行列置換を行います.
sql:
第3歩:第2歩には重複データがあるので、私たちがしなければならないのは重さを取り除くことです.もちろんdistinctキーワードではなく、group byを考えてsum()を加算します.ここで注意しなければならないのは、groupbyはselectの前に実行され、つまりsumの前に実行されるので、部門番号depでグループ化し、グループ内で加算すれば重さを下げることができます.
sql:
ちなみに、さっきインターネットで調べて知った知識を補足します(私がこの問題を解決する鍵です):
SQLが他のプログラミング言語と異なる最も明らかな特徴は、コードを処理する順序である.大数プログラミング言語では,コードは符号化順に処理されるが,SQL言語では,最初に処理される句はFROM句であり,SELECT文が最初に出現するにもかかわらず,ほとんどが最後に処理される.
各ステップでは、次のステップの入力として使用される仮想テーブルが生成されます.これらの仮想テーブルは、呼び出し元(クライアント・アプリケーションまたは外部クエリー)には使用できません.最後のステップで生成されたテーブルだけが呼び出し元に返されます.クエリーに句を指定しない場合は、対応する手順はスキップされます.以下に、SQLサーバ2000およびSQLサーバ2005に適用される各論理ステップについて簡単に説明する.
(
8
)
SELECT
 (
9
)
DISTINCT
  (
11
)
<
Top
 Num
>
 
<
select
 list
>
(
1
)
FROM
 
[
left_table
]
(
3
)
<
join_type
>
 
JOIN
 
<
right_table
>
(
2
)        
ON
 
<
join_condition
>
(
4
)
WHERE
 
<
where_condition
>
(
5
)
GROUP
 
BY
 
<
group_by_list
>
(
6
)
WITH
 
<
CUBE 
|
 RollUP
>
(
7
)
HAVING
 
<
having_condition
>
(
10
)
ORDER
 
BY
 
<
order_by_list
>
論理クエリー処理フェーズの概要
FROM:FROM句の最初の2つのテーブルに対してデカルト積(Cartesian product)を実行し、仮想テーブルVT 1 を生成する.
ON:VT 1にONフィルタを適用します.VT 2が挿入されるのは、実際の行としてのみです.
OUTER(JOIN):OUTER JOIN(CROSS JOINまたは(INNER JOINに対して)を指定すると、保留テーブル(preserved table:左外部結合左テーブルを保留テーブル、右外部結合右テーブルを保留テーブル、完全外部結合両テーブルを保留テーブルと表記)に一致する行が見つからない場合は、外部行としてVT 2に追加する、VT 3を生成する.FROM句に2つ以上のテーブルが含まれている場合、前の結合で生成された結果テーブルと次のテーブルについて、すべてのテーブルが処理されるまで手順1~3を繰り返します.
WHERE:VT 3にWHEREフィルタを適用する.TRueとする行のみVT 4が挿入される.
GROUP BY:GROUP BY句中の列リスト対VT 4中の行グループを押す、VT 5を生成する.
CUBE|ROLLUP:スーパーグループをVT 5に挿入し、VT 6を生成する.
HAVING:VT 6にHAVINGフィルタを適用します.VT 7は、trueとするグループのみ挿入される.
SELECT:SELECTリストを処理し、VT 8を生成する.
DISTINCT:重複する行をVT 8から除去し、VT 9を生成する.
ORDER BY:VT 9中の行をORDER BY句中の列リスト順に並べ替える、カーソル(VC 10)を生成する.
TOP:VC 10の先頭から指定された数または割合の行を選択し、テーブルVT 11を生成し、呼び出し元に戻る.
注意:ステップ10で、ORDER BY句の列のリストに従って、前のステップで戻る行を並べ替え、カーソルVC 10を返す.このステップは、最初のステップであり、SELECTリストのカラムエイリアスを使用できる唯一のステップです.このステップは、他のステップとは異なり、有効なテーブルではなくカーソルを返します.SQLは集合理論に基づいている.集合は事前に行をソートしません.メンバーの論理集合にすぎません.メンバーの順序は重要ではありません.テーブルをソートしたクエリーは、特定の物理的順序で整理されたローを含むオブジェクトを返します.ANSIはこのオブジェクトをカーソルと呼ぶ.このステップを理解することは、SQLを正しく理解するための基礎です.
このステップはテーブルを返さない(カーソルを返す)ため、ORDER BY句を使用したクエリはテーブル式として使用できません.表式には、ビュー、インライン表値関数、サブクエリ、派生表、共通式が含まれます.その結果は、物理的な記録が期待されるクライアントアプリケーションに返さなければなりません.たとえば、次の派生テーブルクエリが無効であり、エラーが発生します.
select * 
from(select orderid,customerid from orders order by orderid) 
as d

次のビューでもエラーが発生します
create view my_view
as
select *
from orders
order by orderid

SQLでは、テーブル式ではORDER BY句を含むクエリは使用できませんが、T-SQLでは例外があります(TOPオプションを適用).
テーブル内のローに特定の順序を仮定しないでください.すなわち、行を整列させると判断しない限り、ORDER BY句を指定しないでください.ソートにはコストがかかります.SQL Serverでは、順序付きインデックススキャンを実行するか、ソート演算子を使用する必要があります.
ああ、やはり私は料理が多すぎて、このような簡単な問題は一日中できます.がんばれ!ハハハ!!!