F(nb=(rvs[2], rvs[3]), potential=QuadraticPotential(A=-0.5 * np.eye(2), b=np.array([1., 2.]), c=0.)) # ensure normalizability ] # all disc potentials must be converted to TablePotential to be used by baseline for factor in factors: if factor.domain_type == 'd' and not isinstance(factor.potential, TablePotential): assert isinstance(factor.potential, MLNPotential), 'currently can only handle MLN' factor.potential = utils.convert_disc_MLNPotential_to_TablePotential( factor.potential, factor.nb) utils.set_log_potential_funs( factors, skip_existing=False) # create lpot_funs to be used by baseline g = Graph() # not really needed here; just to conform to existing API g.rvs = rvs g.factors = factors g.init_nb() g.init_rv_indices() Vd, Vc, Vd_idx, Vc_idx = g.Vd, g.Vc, g.Vd_idx, g.Vc_idx dstates = [rv.dstates for rv in Vd] names = ('EPBP', 'OSI') num_algos = len(names) mmap_res = np.empty([num_algos, len(rvs)]) algo = 0 name = names[algo]
if dobs == 0: factor.potential = QuadraticPotential( A=np.zeros([1, 1]), b=np.zeros([1]), c=0) else: factor.potential = QuadraticPotential( A=w_h * -np.eye(1), b=w_h * np.array([2 * cobs]), c=w_h * -cobs**2) assert isinstance(factor.potential, (TablePotential, QuadraticPotential, HybridQuadraticPotential)) converted_factors.append(factor) utils.set_log_potential_funs( converted_factors, skip_existing=False) # create lpot_funs to be used by baseline cond_g.init_rv_indices( ) # create indices in the conditional mrf (for baseline and osi) utils.set_nbrs_idx_in_factors( converted_factors, cond_g.Vd_idx, cond_g.Vc_idx) # preprocessing for baseline num_dstates = np.prod([rv.dstates for rv in cond_g.Vd]) print( f'running {algo_name} baseline with {num_dstates} joint discrete configs' ) if baseline == 'exact': bn_res = convert_to_bn(converted_factors, cond_g.Vd,
# for key in key_list: # if key not in data: # ans[key] = bp.map(rvs_table[key]) # guaranteed exact baseline by solving linear equations (marginal means = marginal modes in Gaussians) start_time = time.process_time() mu = utils.get_gaussian_mean_params_from_quadratic_params( A=quadratic_params[0], b=quadratic_params[1], mu_only=True) time_cost[name] = (time.process_time() - start_time) / num_test + time_cost.get(name, 0) for key in key_list: if key not in data: ans[key] = mu[rvs_idx[rvs_table[key]]] name = 'OSI' utils.set_log_potential_funs( g.factors_list) # OSI assumes factors have callable .log_potential_fun K = 1 T = 10 # lr = 1e-1 lr = 5e-1 # its = 1000 its = 500 # fix_mix_its = int(its * 0.1) fix_mix_its = int(its * 1.0) # fix_mix_its = 500 logging_itv = 100 # cond = True cond = True if cond: cond_g.init_nb( ) # this will make cond_g rvs' .nb attributes consistent (baseline didn't care so it was OK)
data[key] = 0 # closed world assumption # data = dict() g, rvs_dict = rel_g.add_evidence(data) print(len(rvs_dict) - len(data)) print(len(g.factors)) obs_rvs = [v for v in g.rvs if v.value is not None] evidence = {rv: rv.value for rv in obs_rvs} cond_g = utils.get_conditional_mrf( g.factors_list, g.rvs, evidence) # this will also condition log_potential_funs cond_g.init_nb( ) # this will make cond_g rvs' .nb attributes consistent (baseline didn't care so it was OK) utils.set_log_potential_funs(cond_g.factors_list, skip_existing=True) print('cond number of rvs', len(cond_g.rvs)) print('cond num drvs', len([rv for rv in cond_g.rvs if rv.domain_type[0] == 'd'])) print('cond num crvs', len([rv for rv in cond_g.rvs if rv.domain_type[0] == 'c'])) for test_num in range(num_tests): test_seed = seed + test_num for algo_num, algo_name in enumerate(algo_names): print('####') print('test_num', test_num) print('running', algo_name) np.random.seed(test_seed + algo_num)
marg_logpdf = utils.curry_epbp_belief(bp, rv, log_belief=True) margs[i] = marg_logpdf elif algo_name in ('OSI', 'LOSI', 'NPVI', 'LNPVI'): cond = True if cond: cond_g.init_nb( ) # this will make cond_g rvs' .nb attributes consistent (baseline didn't care so it was OK) K = 1 T = 3 lr = 0.5 its = 200 fix_mix_its = int(its * 0.5) logging_itv = 50 utils.set_log_potential_funs( g.factors_list, skip_existing=True) # g factors' lpot_fun should still be None # above will also set the lpot_fun in all the (completely unobserved) factors in cond_g if algo_name in ('OSI', 'NPVI'): if cond: # TODO: ugly; fix _g = cond_g else: _g = g if algo_name == 'OSI': vi = OneShot(g=_g, K=K, T=T, seed=seed) else: vi = NPVI(g=_g, K=K, T=T, isotropic_cov=False, seed=seed) else: if cond: cg = CompressedGraphSorted(cond_g) else:
factor.potential, TablePotential): assert isinstance(factor.potential, MLNPotential), 'currently can only handle MLN' factor.potential = utils.convert_disc_MLNPotential_to_TablePotential( factor.potential, factor.nb) if factor.domain_type == 'h': assert isinstance(factor.potential, MLNPotential), 'currently can only handle MLN' factor.potential = equiv_hybrid_pot assert isinstance( factor.potential, (TablePotential, QuadraticPotential, HybridQuadraticPotential)) g2.factors.append(factor) utils.set_log_potential_funs( g2.factors, skip_existing=False) # create lpot_funs to be used by baseline g2.init_rv_indices() Vd, Vc, Vd_idx, Vc_idx = g2.Vd, g2.Vc, g2.Vd_idx, g2.Vc_idx # currently using the same ans if baseline == 'exact': bn_res = convert_to_bn(g2.factors, Vd, Vc, return_logZ=True) bn = bn_res[:-1] logZ = bn_res[-1] print('true -logZ', -logZ) # print('BN params', bn) num_dstates = np.prod(g2.dstates) if num_dstates > 1000: print(
nb=[atom_smoke_x, atom_cancer] ) rel_g = RelationalGraph() rel_g.atoms = (atom_friend, atom_smoke_x, atom_cancer) rel_g.param_factors = (f1, f2) rel_g.init_nb() rel_g.data = data g, rvs_table = rel_g.grounded_graph() print(rvs_table) from OneShot import OneShot utils.set_log_potential_funs(g.factors_list) K = 4 T = 8 osi = OneShot(g=g, K=K, T=T, seed=seed) res = osi.run(lr=1e-1, its=200) for key, rv in sorted(rvs_table.items()): if rv.value is None: # only test non-evidence nodes print(key, osi.map(obs_rvs=[], query_rv=rv)) import matplotlib.pyplot as plt record = res['record'] for key in record: plt.plot(record[key], label=key) plt.legend(loc='best') save_name = __file__.split('.py')[0]