Je travaille sur un algorithme qui doit calculer la taille d'un ensemble généré par les intersections d'au moins 2 ensembles. Plus précisement:
Les ensembles qui sont intersectés sont générés par des requêtes SQL, et dans un effort pour garder les choses rapides, j'obtiens un compte de chaque requête à l'avance, puis je prends l'ensemble avec le plus petit nombre ( ) et j'utilise ces ID comme limites sur le reste des grandes requêtes, donc l'intersection devient effectivement:
Même cette stratégie me laisse de très grosses requêtes à exécuter, car peut parfois être volumineux. Mon idée pour y faire face est de prendre un échantillon aléatoire de A 0 et de l'intersecter avec le reste des ensembles avant d'extrapoler vers une estimation correcte de z . Ma question est la suivante: quelle est la meilleure façon de procéder à l'échantillonnage puis à l'extrapolation pour revenir à une valeur de z qui, si elle n'est pas entièrement exacte, a une plage d'erreur prévisible?
Voici ce que j'ai essayé jusqu'à présent (en pseudocode, en quelque sorte):
sample_threshold := 10000
factor := 1
if (len(A0) > sample_treshold) {
factor = sample_threshold / len(A0)
}
// Take a random sample of size 10000 from A0
// Intersect all the other sets with the A0 sample, then with each other
working_set := A0
for i, a := range A {
a = intersect(A0, a)
working_set = intersect(working_set, a)
}
z := len(working_set) * (1 / factor)
Ce code fonctionne, mais semble constamment surestimer z
, avec une taille d'échantillon inférieure donnant une estimation plus élevée. De plus, je ne sais pas comment cela évoluerait avec plus de deux ensembles à intersecter.
J'espère que cette question a du sens, faites-moi savoir si je peux clarifier davantage. De plus, si cette question est hors sujet ou appartient à un autre endroit, faites-le moi savoir et je serai ravie de la déplacer.
Selon le commentaire de Bill , j'ai effectué quelques essais rapides pour montrer la taille de l'échantillon par rapport à l'erreur. Chaque taille d'échantillon a été exécutée 20 fois, et comme vous pouvez le voir, la tendance est assez claire:
ORDER BY RAND()
, ce qui n'est pas parfait mais devrait convenir à cette tâche.