1

MySQL で中央値を計算する必要があります。ここで解決策を見ました。

しかし、私はそれの一部を理解していませんでした。ここで提供される解決策は次のとおりです。

SELECT x.val from data x, data y
GROUP BY x.val
HAVING SUM(SIGN(1-SIGN(y.val-x.val))) = (COUNT(*)+1)/2

元の質問の文脈ではdata x何ですか?data y通常、FROM の後にテーブル名が続きます。しかし、質問が 1 つのテーブルのみを参照しているのに、なぜ 2 つのテーブルがリストされているのでしょうか? 誰かがこのソリューションの仕組みを説明できますか? また、私はこの部分を理解していませんでした: HAVING SUM(SIGN(1-SIGN(y.val-x.val))).

4

1 に答える 1

2

元の質問の文脈におけるデータ x とデータ y とは何ですか? 通常、FROM の後にテーブル名が続きます。しかし、質問が 1 つのテーブルのみを参照しているのに、なぜ 2 つのテーブルがリストされているのでしょうか?

元の質問でdata x, data yは、テーブルをそれ自体に結合し、デカルト積を作成します。元のテーブルには 7 つの行があり、すべての行を他のすべての行に対して結合することにより、結果の積は 49 行になります。

また、私はこの部分を理解していませんでした: HAVING SUM(SIGN(1-SIGN(y.val-x.val))).

基本的に、この関数はすべての値について、調べている値よりも小さい値がいくつあるかを判断します。次に、この合計をカウントの半分 + 1... と比較し、その値を中央値として選択します。

これは、x.val比較対象の値 ( ) から値 ( ) を減算することによって行われますy.val。次に、関数を使用して、結果を、、またはSIGNに変換します。次に、この値を減算し、再度取得します。したがって、値が比較対象の値より小さい場合、最終結果は. たとえば、is 、およびisとしましょう。-101SIGNy.valx.val1y3x5

3 - 5 = -2
SIGN(-2) = -1
1 - (-1) = 2
SIGN(2) = 1

yだった場合5、そして...xだった場合、最終結果は次のようになります。30

5 - 3 = 2
SIGN(2) = 1
1 - 1 = 0
SIGN(0) = 0

これらの比較の結果を合計すると、調べている値の前にいくつの値があるかを示す数値が得られます。SUM次に、これを比較COUNT(*) + 1 / 2して中間範囲を見つけます...

于 2012-01-28T06:16:49.747 に答える