public static CUDDNode NondetUntil(CUDDNode trans, CUDDNode nondetMask, CUDDVars allRowVars, CUDDVars allColVars, CUDDVars nondetVars, CUDDNode yes, CUDDNode maybe, bool min) { DateTime startTime = DateTime.Now; int numberOfIterations = 0; CUDDNode a, sol, tmp; CUDD.Ref(trans, maybe); a = CUDD.Function.Times(trans, maybe); CUDD.Ref(yes); sol = yes; while (true) { numberOfIterations++; tmp = CUDD.Matrix.MatrixMultiplyVector(a, sol, allRowVars, allColVars); if (min) { CUDD.Ref(nondetMask); tmp = CUDD.Function.Maximum(tmp, nondetMask); tmp = CUDD.Abstract.MinAbstract(tmp, nondetVars); } else { tmp = CUDD.Abstract.MaxAbstract(tmp, nondetVars); } CUDD.Ref(yes); tmp = CUDD.Function.Maximum(tmp, yes); //check convergence if (CUDD.IsEqual(tmp, sol)) { CUDD.Deref(tmp); break; } CUDD.Deref(sol); sol = tmp; } DateTime endTime = DateTime.Now; double runningTime = (endTime - startTime).TotalSeconds; Debug.WriteLine("NondetUntil: " + numberOfIterations + " iterations in " + runningTime + " seconds"); // CUDD.Deref(a); return(sol); }
public static CUDDNode NondetReachReward(CUDDNode trans, CUDDNode reach, CUDDNode stateReward, CUDDNode transReward, CUDDNode nondetMask, CUDDVars allRowVars, CUDDVars allColVars, CUDDVars nondetVars, CUDDNode infReward, CUDDNode maybeReward, bool min) { DateTime startTime = DateTime.Now; int numberOfIterations = 0; CUDDNode a, allReward, newNondetMask, sol, tmp; // filter out rows (goal states and infinity states) from matrix CUDD.Ref(trans, maybeReward); a = CUDD.Function.Times(trans, maybeReward); // also remove goal and infinity states from state rewards vector CUDD.Ref(stateReward, maybeReward); CUDDNode tempStateReward = CUDD.Function.Times(stateReward, maybeReward); // multiply transition rewards by transition probs and sum rows // (note also filters out unwanted states at the same time) CUDD.Ref(transReward, a); CUDDNode tempTransReward = CUDD.Function.Times(transReward, a); tempTransReward = CUDD.Abstract.SumAbstract(tempTransReward, allColVars); // combine state and transition rewards allReward = CUDD.Function.Plus(tempStateReward, tempTransReward); // need to change mask because rewards are not necessarily in the range 0..1 CUDD.Ref(nondetMask); newNondetMask = CUDD.Function.ITE(nondetMask, CUDD.PlusInfinity(), CUDD.Constant(0)); // initial solution is infinity in 'inf' states, zero elsewhere // note: ok to do this because cudd matrix-multiply (and other ops) // treat 0 * inf as 0, unlike in IEEE 754 rules CUDD.Ref(infReward); sol = CUDD.Function.ITE(infReward, CUDD.PlusInfinity(), CUDD.Constant(0)); while (true) { numberOfIterations++; tmp = CUDD.Matrix.MatrixMultiplyVector(a, sol, allRowVars, allColVars); // add rewards CUDD.Ref(allReward); tmp = CUDD.Function.Plus(tmp, allReward); if (min) { CUDD.Ref(newNondetMask); tmp = CUDD.Function.Maximum(tmp, newNondetMask); tmp = CUDD.Abstract.MinAbstract(tmp, nondetVars); } else { tmp = CUDD.Abstract.MaxAbstract(tmp, nondetVars); } CUDD.Ref(infReward); tmp = CUDD.Function.ITE(infReward, CUDD.PlusInfinity(), tmp); if (CUDD.IsEqual(tmp, sol)) { CUDD.Deref(tmp); break; } CUDD.Deref(sol); sol = tmp; } DateTime endTime = DateTime.Now; double runningTime = (endTime - startTime).TotalSeconds; Debug.WriteLine("NondetReachReward: " + numberOfIterations + " iterations in " + runningTime + " seconds"); // CUDD.Deref(a, allReward, newNondetMask); return(sol); }
/// <summary> /// Solve the linear equation system Ax = b with Jacobi /// </summary> /// <param name="a"></param> /// <param name="b"></param> /// <param name="init">initial solution</param> /// <param name="reach"></param> /// <param name="allRowVars"></param> /// <param name="allColVars"></param> /// <param name="omega">jor parameter</param> /// <returns></returns> public static CUDDNode Jacobi(CUDDNode a, CUDDNode b, CUDDNode init, CUDDNode reach, CUDDVars allRowVars, CUDDVars allColVars, double omega) { DateTime startTime = DateTime.Now; int numberOfIterations = 0; CUDDNode id = CUDD.Matrix.Identity(allRowVars, allColVars); CUDD.Ref(reach); id = CUDD.Function.And(id, reach); CUDD.Ref(id, a); CUDDNode diags = CUDD.Function.Times(id, a); diags = CUDD.Abstract.SumAbstract(diags, allColVars); // CUDD.Ref(id, a); CUDDNode newA = CUDD.Function.ITE(id, CUDD.Constant(0), a); newA = CUDD.Function.Times(CUDD.Constant(-1), newA); // divide a,b by diagonal CUDD.Ref(diags); newA = CUDD.Function.Divide(newA, diags); CUDD.Ref(b, diags); CUDDNode newB = CUDD.Function.Divide(b, diags); // print out some memory usage Debug.WriteLine("Iteration matrix MTBDD... [nodes = " + CUDD.GetNumNodes(newA) + "]"); Debug.WriteLine("Diagonals MTBDD... [nodes = " + CUDD.GetNumNodes(diags) + "]"); CUDD.Ref(init); CUDDNode sol = init; while(true) { numberOfIterations++; CUDDNode tmp = CUDD.Matrix.MatrixMultiplyVector(newA, sol, allRowVars, allColVars); CUDD.Ref(newB); tmp = CUDD.Function.Plus(tmp, newB); if(omega != 1) { tmp = CUDD.Function.Times(tmp, CUDD.Constant(omega)); CUDD.Ref(sol); tmp = CUDD.Function.Plus(tmp, CUDD.Function.Times(sol, CUDD.Constant(1 - omega))); } if(CUDD.IsEqual(tmp, sol)) { CUDD.Deref(tmp); break; } CUDD.Deref(sol); sol = tmp; } CUDD.Deref(id, diags, newA, newB); DateTime endTime = DateTime.Now; double runningTime = (endTime - startTime).TotalSeconds; Debug.WriteLine("Jacobi: " + numberOfIterations + " iterations in " + runningTime + " seconds"); return sol; }