0

SQL を使用して、テーブル内のデータを 3 次元でグループ化しようとしています。そのためには、いくつかのグループ化基準に基づいて出力された値を変更する方法が必要です。次に、GROUP コマンドを使用して、最終的に行をグループ化する予定です。

例で説明する方が簡単です。

走る

SELECT b as b_bin
   , l as l_bin
   , k_1AperMag1 as k1_bin
   , count(*) as num
FROM gpssource
WHERE b between -1.1 and 1.1
   and l between 9.9 and 11.6
   and k_1AperMag1 between 0 and 25 
GROUP BY b, l, k_1AperMag1

テーブルを取得します

b_bin               | l_bin              | k1_bin      | num
-1.0115976238979311 | 0.968853586216488  | 13.680575   | 1
-1.0299234557450931 | 11.591887279330654 | 16.761375   | 1
-0.3757959886541285 | 11.446711966673629 | 16.372013   | 1
-0.7250531677528679 | 11.357881248039163 | 17.16921    | 1
...and about 100 million more rows

基本的に、各行を b_bin、l_bin、k1_bin のグループにビン化する必要があります。たとえば、最初の行は ab bin -1.1 -> -1.0, l bin 0.9 -> 1.0 および k1 bin 13 -> 14 に入る必要があります。SQL でこれを行う私の考えは、-1.0115976238979311 を -1.05, 0.968853586216488 に変更することです。 0.95 および 13.680575 から 13.5 に変更し、GROUP by コマンドを使用して実際にそれらをビンにグループ化し、ビンの各セットのカウントを取得します。

私の最終結果は次のようになります。

b_bin | l_bin | k1_bin | num
-1.05 |  0.95 |   13.5 |  23
-0.95 |  0.95 |   13.5 |  20
-0.95 |  0.85 |   13.5 |  25
-0.95 |  0.85 |   12.5 |  23
and more, for each bin in b, l and k1.

最終的に、私はそれをマトリックスに入れて、b と l が x 座標と y 座標であり、k1 が 3d 空間のスライスであるイメージを作成します。 銀河の密度マップ

残念ながら、実際の値からビンの中心値に変更する方法が正確にはわかりません。これはSQLで達成することさえ可能ですか? 私はこれをすべてPythonで動作させていますが、ロジスティック上の理由からSQLを使用してデータをビン化する必要があります。

私の基本的な質問は、SELECT によって出力された値をどのように変更するかということです。format() を使用してさまざまな方法でフォーマットできますが、私が知る限り、出力する値を自分で選択することはできません... SQL には関数もありますか? 私はしばらくグーグルで検索しましたが、問題についてはあまり見つかりませんでした...

どんなポインタでも大歓迎です!

4

1 に答える 1

2

ここで必要な結果を得るためにいくつかの SQL を作成しました: http://www.sqlfiddle.com/#!2/1a54a/1

以下はコードです。これがどれほどうまく機能するかはわかりませんが、試してみることができます:

SET @bbinSize = 0.1;
SET @lbinSize = 0.1;
SET @kbinSize = 1;
SELECT
    bbin,
    lbin,
    kbin,
    COUNT(*)
FROM
(
    SELECT
        a.b,
        a.l,
        a.k_1AperMag1,
        ((FLOOR(((1 / @bbinSize) * a.b)) * @bbinSize) + @bbinSize / 2) bbin,
        ((FLOOR(((1 / @lbinSize) * a.l)) * @lbinSize) + @lbinSize / 2) lbin,
        ((FLOOR(((1 / @kbinSize) * a.k_1AperMag1)) * @kbinSize) + @kbinSize / 2) kbin
    FROM

    MyTable a
    ) bins
GROUP BY 
    bbin,
    lbin,
    kbin

より良いアイデアは、3 つの新しいテーブル を作成し、BBinそれぞれに 3 つの列,を含めることです。次に、各ビンをこれらに入力します。LBinKBinNameMinValueMaxValue

クエリは次のようになります。

SELECT
    BBin.Name,
    LBin.Name,
    KBin.Name
    COUNT(*) as MyCount
FROM
    MyTable
    LEFT JOIN BBin ON MyTable.B >= BBin.MinValue AND MyTable.B < BBin.MaxValue
    LEFT JOIN LBin ON MyTable.L >= LBin.MinValue AND MyTable.L < LBin.MaxValue
    LEFT JOIN KBin ON MyTable.KAperMag1 >= KBin.MinValue AND MyTable.KAperMag1 < KBin.MaxValue
GROUP BY
    BBin.Name
    LBin.Name
    KBin.Name

2 番目のオプションの方がパフォーマンスが良いと思いますが、テストはあなたに任せます。

于 2012-10-23T14:48:40.513 に答える