3

私はクロスフィルターで遊んでいて、それが素晴らしいと感じましたが、最近壁にぶつかりました。私の問題にクロスフィルターが必要かどうかはまったくわかりません代替ソリューションを聞いてうれしいです。

私のデータは次のようになります。

[{ 
year: "1987", 
country: "UK", 
product: "pineapple", 
tons_available: 10, 
tons_sold: 8
},
{ year: "1987", country: "US", product: "pineapple", tons_available: 34, tons_sold: 18},
{ year: "1987", country: "UK", product: "pear", tons_available: 4, tons_sold: 3},
{ year: "1987", country: "US", product: "pear", tons_available: 23, tons_sold: 20},
{ year: "1988", country: "UK", product: "pineapple", tons_available: 12, tons_sold: 3},
{ year: "1988", country: "US", product: "pineapple", tons_available: 56, tons_sold: 6},
{ year: "1988", country: "UK", product: "pear", tons_available: 32, tons_sold: 32},
{ year: "1988", country: "US", product: "pear", tons_available: 31, tons_sold: 8},
and on, and on...]

年間データを集計したいのですが、「tons_available」や「tons_sold」など、すでに利用可能な指標に対して集計できました。

var by_week = data_to_filter.dimension( function(d) { return d.year; });
var tons_sold_by_week = by_week.group()
                         .reduceSum(function(d) { return d.tons_sold; });

ただし、集約されたオブジェクトの上にメトリックを作成する方法が見つかりません。たとえば、年間の販売率を作成したいと考えています。このためには、1 年ごとにすべてのフィールドを合計し、tons_sold/tons_available のように除算する必要があります。

これにより、理想的には次のようにフォーマットされたjsonが得られます。

[{ 
year: "1987", 
tons_available: 71, 
tons_sold: 49
str: 0.69
},
{ year: "1988", tons_available: 131, tons_sold: 49, str: 0.37 },
and on, and on...]

集約されたオブジェクトは、合計された変数のみを保持し、年に 1 つのカップルのキー/値しか得られないように思えます。

私が求めているものを達成する方法はありますか?

どうもありがとう!

4

1 に答える 1

1

これが引き続き役立つことを願っています。

これを行うには、特定のユース ケースに合わせて reduceAdd、reduceRemove、reduceInitial 関数を定義し、それらを reduce に渡します。

コード:

var cf   = crossfilter(data),
    year = cf.dimension(function(d) { return d.year; });

var reduceAdd = function(p, v) {
    p.tons_available += v.tons_available;
    p.tons_sold      += v.tons_sold;
    p.str            = p.tons_sold/p.tons_available;
    return p;
}

var reduceRemove = function(p, v) {
    p.tons_available -= v.tons_available;
    p.tons_sold      -= v.tons_sold;
    p.str            = p.tons_sold/p.tons_available;
    return p;
}

var reduceInitial = function() {
    return {
        tons_available : 0,
        tons_sold      : 0,
        str            : 0
    }
}

var json = year.group().reduce(reduceAdd,reduceRemove,reduceInitial).orderNatural().top(Infinity);

console.log(json);

Crossfilter がレコードを追加するとき、reduceAdd を使用して値を再計算します。Crossfilter がフィルター アウト レコードを削除する場合、reduceRemove を使用して値を更新します。reduceInitial によって提供される初期値が必要です (関数であることに注意してください)。ドキュメントhttps://github.com/square/crossfilter/wiki/API-Reference#group_reduceのパーマリンクを参照してください。

上記の入力を使用しました。これは、結果として取得したjsonです。

[{key: "1988", value: {
    str: 0.37404580152671757,
    tons_available: 131,
    tons_sold: 49},
 {key: "1987", value: {
    str: 0.6901408450704225,
    tons_available: 71,
    tons_sold: 49}]

要求した出力とは正確には異なりますが、かなり近いものです。

于 2014-09-04T20:10:20.003 に答える