誰かが私のために、私が現在使用しているものよりも効率的なデカルト積アルゴリズムを示してくれませんか(あると仮定して)。私はSOを見回して少しググったが、明らかなものが何も見えないので、何かが足りない可能性がある。
foreach (int i in is) {
foreach (int j in js) {
//Pair i and j
}
}
これは、コードで行うことの非常に単純化されたバージョンです。2つの整数は、1つ以上のオブジェクトを取得するために使用されるルックアップキーであり、2つのルックアップからのすべてのオブジェクトがペアになって新しいオブジェクトになります。
はるかに大規模で複雑なシステムのこの小さなコードブロックは、データセットがスケールを超えて動作しているため、パフォーマンスの大きなボトルネックになります。これの一部は、オブジェクトの格納に使用されるデータ構造と関連するルックアップを改善することで軽減できる可能性がありますが、私が感じる主な問題は、デカルト積自体の計算です。
編集
そこで、Marcのコメントに応えて使用できるトリックがあるかどうかを確認するために、アルゴリズムの特定の使用法に関するもう少し背景を説明します。システム全体は、グラフデータのセットに対してSPARQLクエリを処理するSPARQLクエリエンジンです。SPARQLはパターンベースの言語であるため、各クエリは、グラフと照合される一連のパターンで構成されます。後続の2つのパターンに共通の変数がない(互いに素である)場合、クエリ全体の可能なソリューションのセットを取得するには、2つのパターンによって生成されたソリューションのデカルト積を計算する必要があります。パターンはいくつでも存在する可能性があり、クエリが一連の互いに素なパターンで構成されている場合、可能なソリューションでかなり指数関数的な拡張につながる可能性のあるデカルト積を複数回計算する必要があります。
どういうわけか、既存の回答から、適用できるトリックがあるかどうか疑問に思います
アップデート
そのため、デカルト積を実行する必要性を最小限に抑え、クエリエンジンを全体的に最適化するために、実装した内容に関する更新を投稿すると思いました。製品の必要性を完全に排除できるとは限らないことに注意してください。ただし、ほとんどの場合、最適化できるため、結合される2つのセットのサイズははるかに小さくなります。
トリプルパターンのセットである各BGP(基本グラフパターン)はブロックとして(本質的に)実行されるため、エンジンは最適なパフォーマンスを得るために、BGP内でパターンを自由に並べ替えることができます。たとえば、次のBGPについて考えてみます。
?a :someProperty ?b .
?c :anotherProperty ?d .
?b a :Class .
最初のパターンの結果は2番目のパターンと互いに素であり、最初の2つのパターンの結果は個々の結果のデカルト積であるため、クエリをそのまま実行するにはデカルト積が必要です。3番目のパターンは最初のパターンの可能な結果を制限するため、この結果には実際に必要な結果よりもはるかに多くの結果が含まれますが、この制限はその後まで適用されません。しかし、そのように再注文した場合:
?b a :Class .
?a :someProperty ?b .
?c :anotherProperty ?d .
2番目と3番目のパターンはまだばらばらであるため、最終結果を得るにはデカルト積が必要ですが、並べ替えることにより、2番目のパターンの結果のサイズを制限します。つまり、デカルト積のサイズははるかに小さくなります。
他にもさまざまな最適化がありますが、SPARQLエンジンの内部についてかなり詳細に説明し始めているので、ここではそれらを投稿しません。詳細に興味のある方は、コメントを残すか、ツイートを送ってください@RobVesse