CBNet* CreateBNet()
{
	// Creation Water-Sprinkler Bayesian network

	const int numOfNds = 4;//*<-

	// 1 STEP:
	// need to specify the graph structure of the model;
	// there are two way to do it

	CGraph *pGraph;

		// Graph creation using neighbors list

		int numOfNbrs[numOfNds] = { 2, 2, 2, 2 };//*<-
		int nbrs0[] = { 1, 2 };//*<-
		int nbrs1[] = { 0, 3 };//*<-
		int nbrs2[] = { 0, 3 };//*<-
		int nbrs3[] = { 1, 2 };//*<-

		// number of neighbors for every node
		int *nbrs[] = { nbrs0, nbrs1, nbrs2, nbrs3 };//*<-

		// neighbors can be of either one of the three following types:
		// a parent, a child (for directed arcs) or just a neighbor (for undirected graphs).
		// Accordingly, the types are ntParent, ntChild or ntNeighbor.

		ENeighborType nbrsTypes0[] = { ntChild, ntChild };//*<-
		ENeighborType nbrsTypes1[] = { ntParent, ntChild };//*<-
		ENeighborType nbrsTypes2[] = { ntParent, ntChild };//*<-
		ENeighborType nbrsTypes3[] = { ntParent, ntParent };//*<-

		ENeighborType *nbrsTypes[] = { nbrsTypes0, nbrsTypes1,nbrsTypes2, nbrsTypes3 };//*<-

		// this is creation of a directed graph for the BNet model using neighbors list
		pGraph = CGraph::Create( numOfNds, numOfNbrs, nbrs, nbrsTypes );

	// 2 STEP:
	// Creation NodeType objects and specify node types for all nodes of the model.

	nodeTypeVector  nodeTypes;

	// number of node types is 1, because all nodes are of the same type
	// all four are discrete and binary
	CNodeType nt(1,2);//*<-
	nodeTypes.push_back(nt);

	intVector nodeAssociation;
	// reflects association between node numbers and node types
	// nodeAssociation[k] is a number of node type object in the
	// node types array for the k-th node
	nodeAssociation.assign(numOfNds, 0);

	// 2 STEP:
	// Creation base for BNet using Graph, types of nodes and nodes association

	CBNet* pBNet = CBNet::Create( numOfNds, nodeTypes, nodeAssociation, pGraph );

	// 3 STEP:
	// Allocation space for all factors of the model
	pBNet->AllocFactors();

	// 4 STEP:
	// Creation factors and attach their to model

	//create raw data tables for CPDs
	float table0[] = { 0.5f, 0.5f };//*<-
	float table1[] = { 0.5f, 0.5f, 0.9f, 0.1f };
	float table2[] = { 0.8f, 0.2f, 0.2f, 0.8f };
	float table3[] = { 1.0f, 0.0f, 0.1f, 0.9f, 0.1f, 0.9f, 0.01f, 0.99f };

	float* table[] = { table0, table1, table2, table3 };//*<-

	int i;
	for( i = 0; i < numOfNds; ++i )
	{
		pBNet->AllocFactor(i);

		CFactor* pFactor = pBNet->GetFactor(i);

		pFactor->AllocMatrix( table[i], matTable );
	}

	return pBNet;
}
Ejemplo n.º 2
0
int testShrinkObservedNodes()
{
    int i/*,j*/;
    int ret = TRS_OK;
    /*prepare to read the values from console*/
    EDistributionType dt;
    int disType = -1;
    EFactorType pt;
    int paramType = -1;
    /*read int disType corresponding DistributionType*/
    while((disType<0)||(disType>0))/*now we have only Tabulars&Gaussian*/
    {
	trsiRead( &disType, "0", "DistributionType");
    }
    /*read int paramType corresponding FactorType*/
    while((paramType<0)||(paramType>2))
    {
	trsiRead( &paramType, "0", "FactorType");
    }
    dt = EDistributionType(disType);
    pt = EFactorType(paramType);
    int numberOfNodes = 0;
    /*read number of nodes in Factor domain*/
    while(numberOfNodes<=0)
    {
	trsiRead( &numberOfNodes, "1", "Number of Nodes in domain");
    }
    int numNodeTypes = 0;
    /*read number of node types in model*/
    while(numNodeTypes<=0)
    {
	trsiRead( &numNodeTypes, "1", "Number of node types in Domain");
    }
    //int seed1 = pnlTestRandSeed()/*%100000*/;
    /*create string to display the value*/
    /*	char *value = new char[20];
    value = _itoa(seed1, value, 10);
    trsiRead(&seed1, value, "Seed for srand to define NodeTypes etc.");
    delete []value;
    trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "seed for rand = %d\n", seed1);
    int *domain = (int *)trsGuardcAlloc(numberOfNodes, sizeof(int));
    CNodeType * allNodeTypes = (CNodeType*)trsGuardcAlloc(numNodeTypes,
    sizeof(CNodeType));
    //To generate the NodeTypes we use rand()% and creates only Tabular now
    for(i=0; i<numNodeTypes; i++)
    {
    allNodeTypes[i] = CNodeType(1, 1+rand()%(numNodeTypes+3));
    }
    */	
    
    /*load data for parameter::ShrinkObservedNodes from console*/
    intVector domain;
    domain.assign( numberOfNodes, 0 );
    nodeTypeVector allNodeTypes;
    allNodeTypes.assign( numNodeTypes, CNodeType() );
    /*read node types*/
    for(i=0; i < numNodeTypes; i++)
    {
	int IsDiscrete = -1;
	int NodeSize = -1;
	while((IsDiscrete<0)||(IsDiscrete>1))
	    /*now we have tabular & Gaussian nodes!! */
	    trsiRead(&IsDiscrete, "1", "Is the node discrete?");
	while(NodeSize<0)
	    trsiRead(&NodeSize, "2", "NodeSize of node");
	allNodeTypes[i] = CNodeType( IsDiscrete != 0, NodeSize );
    }
    const CNodeType **nodeTypesOfDomain = (const CNodeType**)
	trsGuardcAlloc(numberOfNodes, sizeof(CNodeType*));
    int numData = 1;
    int *Ranges = (int*)trsGuardcAlloc(numberOfNodes, sizeof(int));
    /*associate nodes to node types*/
    for(i=0; i<numberOfNodes; i++)
    {
	domain[i] = i;
	int nodeAssociationToNodeType = -1;
	while((nodeAssociationToNodeType<0)||(nodeAssociationToNodeType>=
	    numNodeTypes))
	    trsiRead(&nodeAssociationToNodeType, "0", 
	    "node i has type nodeAssociationToNodeType");
	nodeTypesOfDomain[i] = &allNodeTypes[nodeAssociationToNodeType];
	//	nodeTypesOfDomain[i] = &allNodeTypes[rand()%numNodeTypes];
	Ranges[i] = nodeTypesOfDomain[i]->GetNodeSize();
	numData=numData*Ranges[i];
    }
    
    CModelDomain* pMD = CModelDomain::Create( allNodeTypes, domain );
    
    /*create factor according all information*/
    CFactor *pMyParam = NULL;
    float *data = (float *)trsGuardcAlloc(numData, sizeof(float));
    char *stringVal;/* = (char*)trsGuardcAlloc(50, sizeof(char));*/
    double val=0;
    /*read the values from console*/
    if(pt == ftPotential)
    {
	pMyParam = CTabularPotential::Create( &domain.front(), numberOfNodes, pMD );
	/*here we can create data by multiply on 0.1 - numbers are nonnormalized*/
	for(i=0; i<numData; i++)
	{
	    val = 0.1*i;
	    stringVal = trsDouble(val);
	    trsdRead(&val, stringVal, "value of i's data position");
	    data[i] = (float)val;
	    //data[i] = (float)rand()/1000;
	}
    }
    else
    {
    /*we can only read data from console - it must be normalized!!
	(according their dimensions) - or we can normalize it by function!*/
	if(pt == ftCPD)
	    pMyParam = CTabularCPD::Create( &domain.front(), numberOfNodes, pMD );
	for(i=0; i<numData; i++)
	{
	    val = -1;
	    while((val<0)||(val>1))
	    {
		trsdRead(&val, "-1", "value of (2*i)'s data position");
	    }
	    data[i] = (float)val;
	}
    }
    //trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "data for Factor = %d\n", data[i]);
    pMyParam->AllocMatrix(data,matTable);
    int nObsNodes = 0;	/*rand()%numberOfNodes;*/
    while((nObsNodes<=0)||(nObsNodes>numberOfNodes))
    {
	trsiRead(&nObsNodes, "1", "Number of Observed Nodes");
    }
    intVector myHelpForEvidence = intVector(domain.begin(), domain.end() );
    int *ObsNodes = (int *)trsGuardcAlloc(nObsNodes, sizeof(int));
    valueVector TabularValues;
    TabularValues.assign( nObsNodes, (Value)0 );
    char *strVal;
    for(i=0; i<nObsNodes; i++)
    {
	//fixme - we need to have noncopy only different ObsNodes
	/*		j = rand()%(numberOfNodes-i);*/
	int numberOfObsNode = -1;
	strVal = trsInt(i);
        intVector::iterator j = std::find( myHelpForEvidence.begin(), myHelpForEvidence.end(), numberOfObsNode );
	while((numberOfObsNode<0)||(numberOfObsNode>numberOfNodes)||
	    (j==myHelpForEvidence.end()))
	{
	    trsiRead(&numberOfObsNode, strVal,"Number of i's observed node");
	    j = std::find(myHelpForEvidence.begin(), myHelpForEvidence.end(),
		numberOfObsNode);
	}
	//ObsNodes[i] = myHelpForEvidence[j];
	myHelpForEvidence.erase( j );
	ObsNodes[i] = numberOfObsNode;
	int valueOfNode = -1;
	int maxValue = (*nodeTypesOfDomain[ObsNodes[i]]).GetNodeSize();
	while((valueOfNode<0)||(valueOfNode>=maxValue))
	{
	    trsiRead(&valueOfNode,"0","this is i's observed node value");
	}
	TabularValues[i].SetInt(valueOfNode);
	/*rand()%((*nodeTypesOfDomain[ObsNodes[i]]).pgmGetNodeSize());*/
    }
    CEvidence* pEvidence = CEvidence::Create( pMD, nObsNodes, ObsNodes, TabularValues );
    myHelpForEvidence.clear();
    CNodeType *ObservedNodeType = (CNodeType*)trsGuardcAlloc(1, 
	sizeof(CNodeType));
    *ObservedNodeType = CNodeType(1,1);
    CPotential *myTakedInFactor = static_cast<CPotential*>(pMyParam)->ShrinkObservedNodes(pEvidence);
    const int *myfactorDomain;
    int factorDomSize ;
    myTakedInFactor->GetDomain(&factorDomSize, &myfactorDomain);
#if 0
    CNumericDenseMatrix<float> *mySmallMatrix = static_cast<
        CNumericDenseMatrix<float>*>(myTakedInFactor->GetMatrix(matTable));
    int n;
    const float* mySmallData;
    mySmallMatrix->GetRawData(&n, &mySmallData);
    int nDims; // = mySmallMatrix->GetNumberDims();
    const int * mySmallRanges;
    mySmallMatrix->GetRanges(&nDims, &mySmallRanges);
    
    if(nDims!=numberOfNodes)
    {
	ret = TRS_FAIL;
	trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "nDims = %d\n", nDims);
    }
    else
    {
	int numSmallData = 1;
	for(i=0; i<nDims; i++)
	{
	    numSmallData = numSmallData*mySmallRanges[i];
	    trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "Range[%d] = %d\n", i, 
		mySmallRanges[i]);
	}
	for(i=0; i<numSmallData; i++)
	{	
	    trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "mySmallData[%d] = %f ",
		i, mySmallData[i]);
	}
    }
#endif
    //getchar();
    delete(myTakedInFactor);
    delete (pMyParam);
    delete pMD;
    //test gaussian parameter
    nodeTypeVector nTypes;
    nTypes.assign( 2, CNodeType() );
    nTypes[0] = CNodeType( 0, 2 );
    nTypes[1] = CNodeType( 0,1 );
    intVector domn = intVector(3,0);
    domn[1] = 1;
    domn[2] = 1;
    
    CModelDomain* pMD1 = CModelDomain::Create( nTypes, domn );
    
    domn[2] = 2;
    
    CPotential *BigFactor = CGaussianPotential::CreateUnitFunctionDistribution( 
	&domn.front(), domn.size(), pMD1,0 );
    float mean[] = { 1.0f, 3.2f};
    CPotential *SmallDelta = CGaussianPotential::CreateDeltaFunction( &domn.front(), 1, pMD1, mean, 1 );
    domn.resize( 2 );
    domn[0] = 1;
    domn[1] = 2;
    CPotential *SmallFunct = CGaussianPotential::Create( &domn.front(),
	domn.size(),  pMD1);
    float datH[] = { 1.1f, 2.2f, 3.3f };
    float datK[] = { 1.2f, 2.3f, 2.3f, 3.4f, 5.6f, 6.7f, 3.4f, 6.7f, 9.0f };
    SmallFunct->AllocMatrix( datH, matH );
    SmallFunct->AllocMatrix( datK, matK );
    static_cast<CGaussianPotential*>(SmallFunct)->SetCoefficient( 0.2f, 1 );
    CPotential* multFact = BigFactor->Multiply( SmallDelta );
    CPotential* nextMultFact = multFact->Multiply( SmallFunct );
    domn[0] = 0;
    domn[1] = 1;
    CPotential *marginalized = static_cast<CPotential*>(nextMultFact->Marginalize( &domn.front(), domn.size() ));
    int isSpecific = marginalized->IsDistributionSpecific();
    if( isSpecific )
    {
	trsWrite(TW_CON|TW_RUN|TW_DEBUG|TW_LST, "\nGaussian Distribution is specific");
    }
    delete BigFactor;
    delete SmallFunct;
    delete SmallDelta;
    delete pMD1;
    
    int ranges_memory_flag = trsGuardCheck(Ranges);
    int data_memory_flag = trsGuardCheck(data);
    int nodeTypesOfDomain_mem_b = trsGuardCheck(nodeTypesOfDomain);
    int ObsNodes_mem_b = trsGuardCheck(ObsNodes);
    int ObsNodeType_mem_b = trsGuardCheck(ObservedNodeType);
    if(((ranges_memory_flag)||(data_memory_flag)||
	(nodeTypesOfDomain_mem_b)||
	(ObsNodes_mem_b)||(ObsNodeType_mem_b)))
    {
	ret = TRS_FAIL;
	return trsResult( ret, ret == TRS_OK ? "No errors" : 
	"Bad test on ShrinkObservedNodes Method - memory");
    }
    else
    {
	trsGuardFree(ObservedNodeType);
	trsGuardFree(ObsNodes);
	trsGuardFree(nodeTypesOfDomain);
	trsGuardFree(data);
	trsGuardFree(Ranges);
    }			
    return trsResult( ret, ret == TRS_OK ? "No errors" : 
    "Bad test on ShrinkObservedNodes Method");
}
Ejemplo n.º 3
0
CBNet* CreateFourNodeExampleNew(void)
{

    CBNet *pBNet;
    const int nnodes = 4;
    const int numberOfNodeTypes = 2;

    int numOfNeigh[] = { 1, 1, 3, 1 };

    int neigh0[] = { 2 };
    int neigh1[] = { 2 };
    int neigh2[] = { 0, 1, 3 };
    int neigh3[] = { 2 };

    ENeighborType orient0[] = { ntChild };
    ENeighborType orient1[] = { ntChild };
    ENeighborType orient2[] = { ntParent, ntParent, ntChild };
    ENeighborType orient3[] = { ntParent };

    int *neigh[] = { neigh0,  neigh1, neigh2, neigh3 };

    ENeighborType *orient[] = { orient0, orient1, orient2, orient3 };

    CGraph *pGraph = CGraph::Create( nnodes, numOfNeigh, neigh, orient );

    CNodeType *nodeTypes = new CNodeType [numberOfNodeTypes];
    nodeTypes[0].SetType(1, 2);
    nodeTypes[1].SetType(0, 1);

    int *nodeAssociation = new int[nnodes];

    nodeAssociation[0]=0;
    nodeAssociation[1]=1;
    nodeAssociation[2]=1;
    nodeAssociation[3]=1;

    pBNet = CBNet::Create(nnodes, numberOfNodeTypes, nodeTypes, nodeAssociation, pGraph);

    CModelDomain* pMD = pBNet->GetModelDomain();

//number of parameters is the same as number of nodes - one CPD per node
//  CFactor *myParams = new CFactor[1];
    int *nodeNumbers = new int [nnodes];

    int domain0[] = { 0 };
    int domain1[] = { 1 };
    int domain2[] = { 0, 1, 2 };
    int domain3[] = { 2, 3 };
    int *domains[] = { domain0, domain1, domain2, domain3 };
    nodeNumbers[0] = 1;
    nodeNumbers[1] = 1;
    nodeNumbers[2] = 3;
    nodeNumbers[3] = 2;

    pBNet->AllocParameters();

    CFactor *myParams = CTabularCPD::Create( domains[0], nodeNumbers[0], pMD );

// data creation for all CPDs of the model
    float data0[] = { 0.5f, 0.5f };

    myParams->AllocMatrix(data0, matTable);
    pBNet->AttachParameter(myParams);

    float mean0 = 0.0f;
    float cov0 = 1.0f;
    CGaussianCPD* pCPD = CGaussianCPD::Create( domain1, 1, pMD );
    pCPD->AllocDistribution( &mean0, &cov0, 1.0f, NULL);
    pBNet->AttachFactor(pCPD);

    float mean1[] = { 8.0f };
    float mean2[] = { 2.0f };
    float cov1[] = { 1.0f };
    float cov2[] = { 1.0f };

    float weight[] = { 0.01f, 0.03f };
    float weight1[] = { 0.01f };
    const float *pData = weight;
    const float *pData1 = weight1;

    CGaussianCPD* pCPD1 = CGaussianCPD::Create( domain2, 3, pMD );
    int ParentCom[] = { 0, 1 };
    pCPD1->AllocDistribution( mean1, cov1, 0.5f, &pData, &ParentCom[0] );
    pCPD1->AllocDistribution( mean2, cov2, 0.5f, &pData, &ParentCom[1] );
    pBNet->AttachFactor(pCPD1);

    CGaussianCPD* pCPD2 = CGaussianCPD::Create( domain3, 2, pMD );
    pCPD2->AllocDistribution( mean1, cov1, 0.5f, &pData1 );
    pBNet->AttachFactor(pCPD2);


    delete [] nodeTypes;
    return pBNet;
}