AI-NeuralNet-FastSOM

 view release on metacpan or  search on metacpan

FastSOM.xs  view on Meta::CPAN

	XPUSHs(sv_2mortal(newSViv(cy)));
	XPUSHs(sv_2mortal(newSVnv(cd)));
	PUTBACK;
}

SV* _som_map(SV* self) {
        MAGIC		*mg;
	SOM_GENERIC	*som;

	if ( !(mg = selfmagic(self)) )
                croak("self has no magic!\n");
	som = self2somptr(self,mg);

	SvREFCNT_inc(som->map->ref);
	return som->map->ref;
}

SV* _som_output_dim(SV* self) {
	MAGIC		*mg;
	SOM_GENERIC	*som;

	if ( !(mg = selfmagic(self)) )
		croak("self has no magic!\n");
	som = self2somptr(self,mg);

	SvREFCNT_inc(som->output_dim);
	return som->output_dim;
}

void _som_train(SV* self,IV epochs) {
	IV		i,X,Y,bx,by,epoch;
	NV		bd,l,sigma,*n;
	AV		**org,**veg,*sample;
	I32		p,pick,nitems,oitems,vitems;
	MAGIC		*mg;
	SOM_GENERIC	*som;
	bool		wantarray;
	void		(*neiguts)(SOM_GENERIC* som,NV sigma,IV X0,IV Y0,NV* n);
	dXSARGS;

	if ( !(mg = selfmagic(self)) )
		croak("self has no magic!");
	som = self2somptr(self,mg);

	if ( epochs < 1 )
		epochs = 1;

	if ( items < 3 )
		croak("no data to learn");

	oitems = items - 2;
	Newx(org,oitems,AV*);
	Newx(veg,oitems,AV*);

	for ( i=2 ; i<items ; i++ )
		if ( SvTYPE(SvRV(ST(i))) != SVt_PVAV )
			croak("training item %i is not an array ref", (int)i);
		else
			org[i-2] = (AV*)SvRV(ST(i));

	som->LAMBDA = epochs / log( som->Sigma0 );

	X = som->X;
	Y = som->Y;

	nitems = X*Y;
	Newx(n,nitems,NV);

	if ( som->type == SOMType_Torus )
		neiguts = _torus_neiguts;
	else if ( som->type == SOMType_Hexa )
		neiguts = _hexa_neiguts;
	else if ( som->type == SOMType_Rect )
		neiguts = _rect_neiguts;
	else
		croak("unknown type");

	wantarray = GIMME_V == G_ARRAY ? TRUE : FALSE;

	/* should this be moved somewhere more global? */
	if ( !PL_srand_called ) {
		seedDrand01((Rand_seed_t)(time(NULL)+PerlProc_getpid()));
		PL_srand_called = TRUE;
	}

	sp = mark;

	for ( epoch=1 ; epoch<=epochs ; epoch++ ) {
		som->T = epoch;
		sigma = som->Sigma0 * exp(-epoch / som->LAMBDA);
		l = som->L0 * exp(-epoch / epochs);

		Copy(org,veg,oitems,AV*);
		vitems = oitems;

		while ( vitems > 0 ) {

			pick = (I32)(Drand01() * vitems);

			sample = (AV*)veg[pick];

			/* optimize me! */
			for ( p=pick+1 ; p<vitems ; p++ ) veg[p-1] = veg[p];
			vitems--;

			_bmuguts(som,sample,&bx,&by,&bd);

			if ( wantarray ) XPUSHs(newSVnv(bd));

			for ( i=0 ; i<nitems ; i++ ) n[i] = -1;

			neiguts(som,sigma,bx,by,n);

			_adjustn(som,l,sigma,n,sample);

		}
	}

	Safefree(n);
	Safefree(org);
	Safefree(veg);



( run in 0.946 second using v1.01-cache-2.11-cpan-39bf76dae61 )