removed dependency on array_t

This commit is contained in:
Fabrizio Riguzzi 2010-07-27 16:53:47 +02:00
parent 25d1fac007
commit 5a19dd372a
3 changed files with 123 additions and 72 deletions

View File

@ -10,9 +10,7 @@ for the relative license.
#include "util.h"
#include "cuddInt.h"
#include "array.h"
#include "mtr.h"
#include "avl.h"
#include "YapInterface.h"
#include <glib.h>
@ -21,16 +19,35 @@ typedef struct
int var,value;
} factor;
typedef struct
{
int nFact;
factor * factors;
} term;
typedef struct
{
int nTerms;
term * terms;
} expr;
typedef struct
{
int nVal,nBit;
array_t * probabilities;
array_t * booleanVars;
double * probabilities;
DdNode * * booleanVars;
} variable;
typedef struct
{
int nVar;
int nBVar;
variable * varar;
int * bVar2mVar;
} variables;
void createVars(array_t * vars, YAP_Term t,DdManager * mgr, array_t * bVar2mVar,int create_dot, char inames[1000][20]);
void createExpression(array_t * expression, YAP_Term t);
variables createVars(YAP_Term t,DdManager * mgr, int create_dot, char inames[1000][20]);
expr createExpression(YAP_Term t);
void init_my_predicates(void);
int compare(char *a, char *b);
gint my_equal(gconstpointer v,gconstpointer v2);
@ -39,11 +56,11 @@ void dealloc(gpointer key,gpointer value,gpointer user_data);
DdNode * retFunction(DdManager * mgr, array_t * expression,array_t * v);
DdNode * retTerm(DdManager * mgr,array_t *factors,array_t * v);
DdNode * retFactor(DdManager * mgr, factor f, array_t * v);
DdNode * retFunction(DdManager * mgr, expr expression,variables v);
DdNode * retTerm(DdManager * mgr,term t,variables v);
DdNode * retFactor(DdManager * mgr, factor f, variables v);
double Prob(DdNode *node, array_t * vars,array_t * bVar2mVar, GHashTable * nodes);
double Prob(DdNode *node, variables vars,GHashTable * nodes);
double ProbBool(DdNode *node, int bits, int nBit,int posBVar,variable v,
array_t * vars,array_t * bVar2mVar, GHashTable * nodes);
variables vars,GHashTable * nodes);

View File

@ -19,20 +19,20 @@ int correctPosition(int index,variable v, DdNode * node,int posBVar);
DdNode * retFunction(DdManager * mgr,array_t *expression, array_t *v)
DdNode * retFunction(DdManager * mgr,expr expression, variables v)
/* given an expression term1+term2+...+termn, returns the BDD that implements that function */
{
array_t * term;
term term1;
DdNode * tNode, * tmp, *tmp1;
int i;
i=0;
tNode=Cudd_ReadLogicZero(mgr);
Cudd_Ref(tNode);
while(i<array_n(expression))
while(i<expression.nTerms)
{
term=array_fetch(array_t * ,expression,i);
tmp=retTerm(mgr,term,v);
term1=expression.terms[i];
tmp=retTerm(mgr,term1,v);
Cudd_Ref(tmp);
tmp1=Cudd_bddOr(mgr,tNode,tmp);
Cudd_Ref(tmp1);
@ -43,7 +43,7 @@ DdNode * retFunction(DdManager * mgr,array_t *expression, array_t *v)
return tNode;
}
DdNode * retTerm(DdManager * mgr,array_t *term, array_t * v)
DdNode * retTerm(DdManager * mgr,term t, variables v)
/* given a term V1=v1 and V2=v2 ... Vn=vn, returns the BDD that implements that function */
{
factor f;
@ -53,9 +53,9 @@ DdNode * retTerm(DdManager * mgr,array_t *term, array_t * v)
i=0;
fNode=Cudd_ReadOne(mgr);
Cudd_Ref(fNode);
while (i<array_n(term))
while (i<t.nFact)
{
f=array_fetch(factor, term, i);
f=t.factors[i];
tmp=retFactor(mgr,f,v);
Cudd_Ref(tmp);
tmp1= Cudd_bddAnd(mgr,fNode,tmp);
@ -67,7 +67,7 @@ DdNode * retTerm(DdManager * mgr,array_t *term, array_t * v)
return fNode;
}
DdNode * retFactor(DdManager * mgr, factor f, array_t * vars)
DdNode * retFactor(DdManager * mgr, factor f, variables vars)
/* given a factor V=v, returns the BDD that implements that function */
{
int varIndex;
@ -76,19 +76,19 @@ DdNode * retFactor(DdManager * mgr, factor f, array_t * vars)
int bit;
variable v;
DdNode * node, *booleanVar, * tmp;
array_t * booleanVars;
DdNode ** booleanVars;
varIndex=f.var;
value=f.value;
v=array_fetch(variable, vars, varIndex);
v=vars.varar[varIndex];
booleanVars=v.booleanVars;
i=v.nBit-1;
node=Cudd_ReadOne(mgr);
Cudd_Ref(node);
/* booelan var with index 0 in v.booleanVars is the most significant */
do {
booleanVar=array_fetch(DdNode *,booleanVars,i);
booleanVar=booleanVars[i];
bit=value & 01;
if (bit)
{
@ -111,7 +111,7 @@ DdNode * retFactor(DdManager * mgr, factor f, array_t * vars)
double Prob(DdNode *node, array_t * vars,array_t * bVar2mVar, GHashTable * nodes)
double Prob(DdNode *node, variables vars, GHashTable * nodes)
/* compute the probability of the expression rooted at node
nodes is used to store nodes for which the probability has alread been computed
so that it is not recomputed
@ -129,7 +129,7 @@ so that it is not recomputed
if (Cudd_IsConstant(node))
{
value=node->type.value;
return value;
return value;
}
else
{
@ -141,10 +141,10 @@ so that it is not recomputed
}
else
{
mVarIndex=array_fetch(int,bVar2mVar,index);
v=array_fetch(variable,vars,mVarIndex);
mVarIndex=vars.bVar2mVar[index];
v=vars.varar[mVarIndex];
nBit=v.nBit;
res=ProbBool(node,0,nBit,0,v,vars,bVar2mVar,nodes);
res=ProbBool(node,0,nBit,0,v,vars,nodes);
key=(DdNode **)malloc(sizeof(DdNode *));
*key=node;
rp=(double *)malloc(sizeof(double));
@ -156,22 +156,22 @@ so that it is not recomputed
}
double ProbBool(DdNode *node, int bits, int nBit,int posBVar,variable v,
array_t * vars,array_t * bVar2mVar, GHashTable * nodes)
variables vars, GHashTable * nodes)
/* explores a group of binary variables making up the multivalued variable v */
{
DdNode *T,*F;
double p,res;
array_t * probs;
double * probs;
probs=v.probabilities;
if (nBit==0)
{
if (bits>=array_n(probs))
if (bits>=v.nVal)
return 0;
else
{
p=array_fetch(double,probs,bits);
res=p*Prob(node,vars,bVar2mVar,nodes);
p=probs[bits];
res=p*Prob(node,vars,nodes);
return res;
}
}
@ -183,16 +183,16 @@ array_t * vars,array_t * bVar2mVar, GHashTable * nodes)
F = node->type.kids.E;
bits=bits<<1;
res=ProbBool(T,bits+1,nBit-1,posBVar+1,v,vars,bVar2mVar,nodes)+
ProbBool(F,bits,nBit-1,posBVar+1,v,vars,bVar2mVar,nodes);
res=ProbBool(T,bits+1,nBit-1,posBVar+1,v,vars,nodes)+
ProbBool(F,bits,nBit-1,posBVar+1,v,vars,nodes);
return res;
}
else
{
bits=bits<<1;
res=ProbBool(node,bits+1,nBit-1,posBVar+1,v,vars,bVar2mVar,nodes)+
ProbBool(node,bits,nBit-1,posBVar+1,v,vars,bVar2mVar,nodes);
res=ProbBool(node,bits+1,nBit-1,posBVar+1,v,vars,nodes)+
ProbBool(node,bits,nBit-1,posBVar+1,v,vars,nodes);
return res;
}
}
@ -204,6 +204,6 @@ currently explored by ProbBool */
{
DdNode * bvar;
bvar=array_fetch(DdNode *,v.booleanVars,posBVar);
bvar=v.booleanVars[posBVar];
return bvar->index==index;
}

View File

@ -24,9 +24,9 @@ FILE *open_file (char *filename, const char *mode);
void reverse(char s[]);
static int compute_prob(void);
void createVars(array_t * vars, YAP_Term t,DdManager * mgr, array_t * bVar2mVar,int create_dot, char inames[1000][20])
variables createVars(YAP_Term t,DdManager * mgr, int create_dot, char inames[1000][20])
/* adds the boolean variables to the BDD and returns
an array_t containing them (array_t is defined in the util library of glu)
the array vars containing them
returns also the names of the variables to be used to save the ADD in dot format
*/
{
@ -35,10 +35,16 @@ returns also the names of the variables to be used to save the ADD in dot format
variable v;
char numberVar[10],numberBit[10];
double p;
b=0;
variables vars;
vars.varar= (variable *) malloc(0* sizeof(variable));
vars.bVar2mVar=(int *) malloc(0* sizeof(int));
b=0;
vars.nVar=0;
while(YAP_IsPairTerm(t))
{
varTerm=YAP_HeadOfTerm(t);
varIndex=YAP_IntOfTerm(YAP_HeadOfTerm(varTerm));
@ -48,10 +54,18 @@ returns also the names of the variables to be used to save the ADD in dot format
probTerm=YAP_HeadOfTerm(varTerm);
v.nVal=nVal;
v.nBit=(int)ceil(log(nVal)/log(2));
v.probabilities=array_alloc(double,0);
v.booleanVars=array_alloc(DdNode *,0);
v.probabilities=(double *) malloc(nVal* sizeof(double));
v.booleanVars=(DdNode * *) malloc(v.nBit* sizeof(DdNode *));
for (i=0;i<nVal;i++)
{
p=YAP_FloatOfTerm(YAP_HeadOfTerm(probTerm));
v.probabilities[i]=p;
probTerm=YAP_TailOfTerm(probTerm);
}
for (i=0;i<v.nBit;i++)
{
if (create_dot)
{
strcpy(inames[b+i],"X");
@ -61,20 +75,24 @@ returns also the names of the variables to be used to save the ADD in dot format
sprintf(numberBit,"%d",i);
strcat(inames[b+i],numberBit);
}
p=YAP_FloatOfTerm(YAP_HeadOfTerm(probTerm));
array_insert(double,v.probabilities,i,p);
probTerm=YAP_TailOfTerm(probTerm);
array_insert(DdNode *,v.booleanVars,i,Cudd_bddIthVar(mgr,b+i));
array_insert(int,bVar2mVar,b+i,varIndex);
v.booleanVars[i]=Cudd_bddIthVar(mgr,b+i);
vars.bVar2mVar=(int *)realloc(vars.bVar2mVar,(b+i+1)*sizeof(int));
vars.bVar2mVar[b+i]=varIndex;
}
Cudd_MakeTreeNode(mgr,b,nVal,MTR_FIXED);
b=b+nVal;
array_insert(variable,vars,varIndex,v);
Cudd_MakeTreeNode(mgr,b,v.nBit,MTR_FIXED);
b=b+v.nBit;
vars.varar=(variable *) realloc(vars.varar,(varIndex+1)* sizeof(variable));
vars.varar[varIndex]=v;
t=YAP_TailOfTerm(t);
}
vars.nVar=varIndex+1;
vars.nBVar=b;
return vars;
}
void createExpression(array_t * expression, YAP_Term t)
expr createExpression(YAP_Term t)
/* returns the expression as an array_t of terms (cubes) starting from the prolog lists of terms
each term is an array_t of factors obtained from a prolog list of factors
each factor is a couple (index of variable, index of value) obtained from a prolog list containing
@ -84,12 +102,13 @@ two integers
YAP_Term termTerm,factorTerm;
factor f;
int i,j;
array_t * term;
term term1;
expr expression;
expression.terms=(term *)malloc(0 *sizeof(term));
i=0;
while(YAP_IsPairTerm(t))
{
term=array_alloc(factor,0);
term1.factors=(factor *)malloc(0 *sizeof(factor));
termTerm=YAP_HeadOfTerm(t);
j=0;
while(YAP_IsPairTerm(termTerm))
@ -97,14 +116,19 @@ two integers
factorTerm=YAP_HeadOfTerm(termTerm);
f.var=YAP_IntOfTerm(YAP_HeadOfTerm(factorTerm));
f.value=YAP_IntOfTerm(YAP_HeadOfTerm(YAP_TailOfTerm(factorTerm)));
array_insert(factor,term,j,f);
term1.factors=(factor *)realloc(term1.factors,(j+1)* sizeof(factor));
term1.factors[j]=f;
termTerm=YAP_TailOfTerm(termTerm);
j++;
}
array_insert(array_t *,expression,i,term);
term1.nFact=j;
expression.terms=(term *)realloc(expression.terms,(i+1)* sizeof(term));
expression.terms[i]=term1;
t=YAP_TailOfTerm(t);
i++;
}
expression.nTerms=i;
return(expression);
}
static int compute_prob(void)
@ -112,30 +136,30 @@ static int compute_prob(void)
*/
{
YAP_Term out,arg1,arg2,arg3,arg4;
array_t * variables,* expression, * bVar2mVar;
variables vars;
expr expression;
DdNode * function, * add;
DdManager * mgr;
int nBVar,i,j,intBits,create_dot;
FILE * file;
DdNode * array[1];
double prob;
char * onames[1];
char inames[1000][20];
char * names[1000];
GHashTable * nodes; /* hash table that associates nodes with their probability if already
computed, it is defined in glib */
//Cudd_ReorderingType order;
arg1=YAP_ARG1;
arg2=YAP_ARG2;
arg3=YAP_ARG3;
arg4=YAP_ARG4;
mgr=Cudd_Init(0,0,CUDD_UNIQUE_SLOTS,CUDD_CACHE_SLOTS,0);
variables=array_alloc(variable,0);
bVar2mVar=array_alloc(int,0);
create_dot=YAP_IntOfTerm(arg4);
createVars(variables,arg1,mgr,bVar2mVar,create_dot,inames);
//Cudd_PrintInfo(mgr,stderr);
vars=createVars(arg1,mgr,create_dot,inames);
//Cudd_PrintInfo(mgr,stderr);
/* automatic variable reordering, default method CUDD_REORDER_SIFT used */
//printf("status %d\n",Cudd_ReorderingStatus(mgr,&order));
//printf("order %d\n",order);
@ -148,10 +172,10 @@ static int compute_prob(void)
*/
expression=array_alloc(array_t *,0);
createExpression(expression,arg2);
expression=createExpression(arg2);
function=retFunction(mgr,expression,vars);
function=retFunction(mgr,expression,variables);
/* the BDD build by retFunction is converted to an ADD (algebraic decision diagram)
because it is easier to interpret and to print */
add=Cudd_BddToAdd(mgr,function);
@ -160,7 +184,7 @@ static int compute_prob(void)
if (create_dot)
/* if specified by the user, a dot file for the BDD is written to cpl.dot */
{
nBVar=array_n(bVar2mVar);
nBVar=vars.nBVar;
for(i=0;i<nBVar;i++)
names[i]=inames[i];
array[0]=add;
@ -179,13 +203,23 @@ static int compute_prob(void)
{
dividend=(dividend<<1)+1;
}
out=YAP_MkFloatTerm(Prob(add,variables,bVar2mVar,nodes));
prob=Prob(add,vars,nodes);
out=YAP_MkFloatTerm(prob);
g_hash_table_foreach (nodes,dealloc,NULL);
g_hash_table_destroy(nodes);
Cudd_Quit(mgr);
array_free(variables);
array_free(bVar2mVar);
array_free(expression);
for(i=0;i<vars.nVar;i++)
{
free(vars.varar[i].probabilities);
free(vars.varar[i].booleanVars);
}
free(vars.varar);
free(vars.bVar2mVar);
for(i=0;i<expression.nTerms;i++)
{
free(expression.terms[i].factors);
}
free(expression.terms);
return(YAP_Unify(out,arg3));
}
/*