(PHP 8 >= 8.4.0)
Pdo\Sqlite::createAggregate — Enregistre une fonction utilisateur d'agrégation pour une utilisation dans les instructions SQL
$name
,$step
,$finalize
,$numArgs
= -1Cette méthode est similaire à Pdo\Sqlite::createFunction() sauf qu'elle enregistre des fonctions qui peuvent être utilisées pour calculer un résultat agrégé sur l'ensemble des lignes d'une requête.
La principale différence entre cette méthode et Pdo\Sqlite::createFunction() est que deux fonctions sont nécessaires pour gérer l'agrégation.
En utilisant cette méthode, il est possible de remplacer les fonctions SQL natives.
name
step
Cette fonction doit être définie comme suit :
context
null
pour la première ligne ; sur les lignes suivantes, elle aura la valeur
qui a été précédemment retournée par la fonction de rappel ; vous devez utiliser
ceci pour maintenir l'état de l'agrégation.
rownumber
value
values
context
dans l'appel suivant de la fonction de rappel ou
de finalisation.
finalize
Cette fonction doit être définie comme suit :
context
Contient la valeur de retour du tout dernier appel à la fonction de rappel.
rowcount
Contient le nombre de lignes sur lesquelles l'agrégation a été effectuée.
numArgs
Exemple #1 Pdo\Sqlite::createAggregate() example
Dans cette exemple, nous allons créer une fonction d'agrégation personnalisée nommée
max_length
qui peut être utilisée dans les requêtes SQL.
Dans cet exemple, nous allons créer une fonction d'agrégation nommée
max_length
qui va calculer la longueur de la chaîne la plus longue
dans l'une des colonnes de la table.
Pour chaque ligne, la fonction max_len_step
est appelée et
passe un paramètre $context
.
Le paramètre de contexte est comme n'importe quelle autre variable PHP et peut être
défini pour contenir un array ou même un object.
Dans cet exemple, nous l'utilisons pour contenir la longueur maximale que nous avons vue jusqu'à présent ;
si la $string a une longueur plus longue que la longueur maximale actuelle,
nous mettons à jour le contexte pour contenir cette nouvelle longueur maximale.
Après que toutes les lignes ont été traitées,
SQLite appelle la fonction max_len_finalize
pour déterminer
le résultat agrégé.
Il est possible d'effectuer un certain type de calcul basé sur les données dans $context
.
Dans cet exemple de base, le résultat a été calculé au fur et à mesure que la requête progressait,
donc la valeur de contexte peut être directement retournée.
<?php
$data = [
'one',
'two',
'three',
'four',
'five',
'six',
'seven',
'eight',
'nine',
'ten',
];
$db = new Pdo\Sqlite('sqlite::memory:');
$db->exec("CREATE TABLE strings(a)");
$insert = $db->prepare('INSERT INTO strings VALUES (?)');
foreach ($data as $str) {
$insert->execute(array($str));
}
$insert = null;
function max_len_step($context, $row_number, $string)
{
if (strlen($string) > $context) {
$context = strlen($string);
}
return $context;
}
function max_len_finalize($context, $row_count)
{
return $context === null ? 0 : $context;
}
$db->createAggregate('max_len', 'max_len_step', 'max_len_finalize');
var_dump($db->query('SELECT max_len(a) from strings')->fetchAll());
?>
Il n'est PAS recommandé de stocker une copie des valeurs dans le contexte et de les traiter à la fin, car vous obligeriez SQLite à utiliser beaucoup de mémoire pour traiter la requête - imaginez combien de mémoire vous auriez besoin si un million de lignes étaient stockées en mémoire, chacune contenant une chaîne de 32 octets de longueur.