Agregados del lenguaje Perl
Este ejemplo utiliza el siguiente nombre de archivo: ' Maxae.pm.
Código
El código de este ejemplo es ligeramente más largo que el del ejemplo agregado en lenguaje C, ya que el código maneja todos los tipos de datos posibles.
package Maxae;
use nzae::Ae;
use strict;
use autodie;
our @ISA = qw(nzae::Ae);
my $ae = Maxae->new();
$ae->run();
# The runUda function here is the exact function implemented for the Ae class
# Reproducing this function is not needed in user code to run an aggregate
# as it is inherited. The user can however override this function to have
# finer control on the running of the aggregate Ae
sub runUda
{
my $self = shift;
while(1)
{
my $aggregationType = $self->_getNextAggregation();
if ( $aggregationType == $self->getAggregateTypeInitialize() )
{
$self->_initializeState();
$self->_saveAggregateResult();
}
elsif ( $aggregationType == $self->getAggregateTypeAccumulate() )
{
$self->_accumulate($self->getState(), $self->getInputRow());
$self->_saveAggregateResult();
}
elsif ( $aggregationType == $self->getAggregateTypeMerge() )
{
$self->_merge($self->getState(), $self->getInputState());
$self->_saveAggregateResult();
}
elsif ( $aggregationType == $self->getAggregateTypeFinalResult() )
{
my $result = $self->_finalResult($self->getState());
$self->_setAggregateResult($result, 1);
$self->_saveAggregateResult();
}
elsif ( $aggregationType == $self->getAggregateTypeEnd() )
{
return;
}
elsif ( $aggregationType == $self->getAggregateTypeError() )
{
croak(nzae::Exceptions::AeInternalError->new("Error calling
nzaeAggNext(). Cause unknown."));
}
else
{
croak(nzae::Exceptions::AeInternalError->new("Received unknown
aggregation type."));
}
}
}
#the functions below need to be overridden by the user
#while writing an aggregate Ae
sub _initializeState
{
my $self = shift;
$self->_setState(0, -2147483647);
}
sub _accumulate
{
my $self = shift;
my @instate = shift;
my @row = shift;
my $state = pop(@instate);
if (scalar(@row) > 0)
{
if ( defined $row[0] )
{
unless (defined $state)
{
if (defined $row[0])
{
$state = $row[0];
}
}
elsif ( $state < $row[0] )
{
if (defined $row[0])
{
$state = $row[0];
}
}
}
}
unless (defined $state)
{
$state = -2147483647;
}
$self->_setState(0, $state);
}
sub _merge
{
my $self = shift;
my @instate = shift;
my @inputValues = shift;
my $state = pop(@instate);
for ( my $i = 0 ; $i < scalar(@inputValues); $i++ )
{
unless (defined $state)
{
$state = $inputValues[$i];
}
elsif ( $state < $inputValues[$i] )
{
$state = $inputValues[$i];
}
}
unless (defined $state)
{
$state = -2147483647;
}
$self->_setState(0, $state);
}
sub _finalResult
{
my $self = shift;
my @state = shift;
my $ret = defined $state[0]? $state[0] : -2147483647;
return $ret;
}
1;
En el ejemplo, se anula la función " runUda ". Como se describe en los comentarios del ejemplo, esta función ya se hereda de la clase ' nzae::Ae ' y no necesita ser sobrescrita por el usuario. No obstante, la función puede anularse si se necesita un control más preciso del funcionamiento del AE.
- Crear un archivo de módulo Perl. En el ejemplo anterior es ' MaxAe.pm.
- Importa e instanciar la clase '
nzae::Ae' en el archivo. - Importar '
autodie' para manejar excepciones no manejadas durante el curso de la ejecución. - Anula la función '
_initializeState' para inicializar la variable de estado definida en el paso de registro. - Reemplaza el método accumulate para implementar la funcionalidad de agregación para cada dataslice.
- Sustituye el método merge para implementar la agregación de variables de estado de cada dataslice.
- Anula el método '
finalResult' para devolver la variable de estado fusionada. - Ejecuta el método ' run() ' del objeto '
nzae::Ae'. - Dado que se trata de un módulo Perl, el archivo debe contener un "1" al final del archivo ' MaxAe.pm.
virtual
$NZ_EXPORT_DIR/ae/utilities/bin/compile_ae --language perl --version 3 \
--template deploy Maxae.pm;Registro
$NZ_EXPORT_DIR/ae/utilities/bin/register_ae --language perl --version 3 \
--template uda --exe Maxae.pm --sig "maxaepl(int)" --return int4 \
--state "(int4)"En ejecución
CREATE TABLE grp_test (grp int4, val int4);
CREATE TABLE
INSERT INTO grp_test VALUES (1, 1);
INSERT 0 1
INSERT INTO grp_test VALUES (1, 2);
INSERT 0 1
INSERT INTO grp_test VALUES (1, 3);
INSERT 0 1
INSERT INTO grp_test VALUES (2, 4);
INSERT 0 1
SELECT maxaepl(val) FROM grp_test;
MAXAEPL
---------
4
(1 row)
SELECT grp, maxaepl(val) FROM grp_test GROUP BY grp;
GRP | MAXAEPL
-----+---------
2 | 4
1 | 3
(2 rows)
SELECT grp, maxaepl(val) over (partition BY grp) FROM grp_test;
GRP | MAXAEPL
-----+---------
1 | 3
1 | 3
1 | 3
2 | 4
(4 rows)