Пример #1
0
variable_idx_t ilp_problem_t::add_variable_of_edge(
    pg::edge_idx_t idx, double coef, bool do_add_constraint_for_node)
{
    const pg::edge_t &edge = m_graph->edge(idx);

    if (ms_do_economize)
    {
        variable_idx_t var(-1);

        if (edge.is_chain_edge())
            variable_idx_t var = find_variable_with_hypernode(edge.head());
        if (edge.is_unify_edge() and edge.head() < 0)
            variable_idx_t var = find_variable_with_hypernode(edge.tail());

        if (var >= 0)
        {
            m_map_edge_to_variable[idx] = var;
            return var;
        }
    }

    variable_idx_t var = add_variable(variable_t(
        util::format("edge(%d):hn(%d,%d)", idx, edge.tail(), edge.head()), 0.0));

    if (do_add_constraint_for_node)
    {
        variable_idx_t v_tail = find_variable_with_hypernode(edge.tail());
        variable_idx_t v_head = find_variable_with_hypernode(edge.head());

        /* IF THE EDGE IS TRUE, TAIL AND HEAD MUST BE TRUE, TOO. */
        if (v_tail >= 0 and (v_head >= 0 or edge.head() < 0))
        {
            constraint_t con(
                util::format("e_hn_dependency:e(%d):hn(%d,%d)",
                       idx, edge.tail(), edge.head()),
                OPR_GREATER_EQ, 0.0);
            
            con.add_term(v_tail, 1.0);
            if (edge.head() >= 0)
                con.add_term(v_head, 1.0);
            con.add_term(var, -1.0 * con.terms().size());
            add_constraint(con);
        }

        /* IF LITERAL NODES IN THE HEAD ARE TRUE, THE NODE MUST BE TRUE, TOO. */
        if (edge.is_chain_edge() and v_head >= 0)
        {
            constraint_t con(
                util::format("n_e_dependency:e(%d)", idx), OPR_GREATER_EQ, 0.0);
            con.add_term(v_head, -1.0);
            con.add_term(var, con.terms().size());
            add_constraint(con);
        }
    }

    m_map_edge_to_variable[idx] = var;
    return var;
}
Пример #2
0
variable_idx_t ilp_problem_t::add_variable_of_hypernode(
    pg::hypernode_idx_t idx, double coef, bool do_add_constraint_for_member)
{
    const std::vector<pg::node_idx_t> &hypernode = m_graph->hypernode(idx);
    if (hypernode.empty()) return -1;

    if (ms_do_economize)
    {
        /* IF A HYERNODE INCLUDE ONLY ONE LITERAL-NODE,
        * USE THE NODE'S VARIABLE AS THE HYPERNODE'S VARIABLE. */
        if (hypernode.size() == 1)
        {
            const pg::node_t &node = m_graph->node(hypernode.front());
            if (not node.is_equality_node() and not node.is_non_equality_node())
            {
                variable_idx_t var = find_variable_with_node(hypernode.front());
                if (var >= 0)
                {
                    m_map_hypernode_to_variable[idx] = var;
                    return var;
                }
            }
        }
    }

    std::string nodes =
        util::join(hypernode.begin(), hypernode.end(), ",");
    std::string name = util::format("hn(%d):n(%s)", idx, nodes.c_str());
    variable_idx_t var = add_variable(variable_t(name, coef));

    if (do_add_constraint_for_member)
    {
        /* FOR A HYPERNODE BEING TRUE, ITS ALL MEMBERS MUST BE TRUE TOO. */
        constraint_t cons(
            util::format("hn_n_dependency:hn(%d):n(%s)", idx, nodes.c_str()),
            OPR_GREATER_EQ, 0.0);
        for (auto n = hypernode.begin(); n != hypernode.end(); ++n)
        {
            variable_idx_t v = find_variable_with_node(*n);
            if (v < 0) return -1;
            cons.add_term(v, 1.0);
        }

        cons.set_bound(0.0, 1.0 * (cons.terms().size() - 1));
        cons.add_term(var, -1.0 * cons.terms().size());
        add_constraint(cons);
    }

    m_map_hypernode_to_variable[idx] = var;
    return var;
}
Пример #3
0
inline
factory_t make_factory()
{
	factory_t f;
	
	f.add
	(
		hopp::is_integer,
		[](std::string const & string) -> expression_t { return constant_t(std::stoi(string)); }
	);
	
	f.add
	(
		[](std::string const & string) -> bool
		{
			return std::find_if(string.begin(), string.end(), [](char const c) { return std::isalpha(c) == false; }) == string.end();
		},
		[](std::string const & string) -> expression_t { return variable_t(string, 0); }
	);
	
	f.add
	(
		[](std::string const & string) -> bool
		{
			return (string == "+" || string == "-" || string == "*" || string == "/" || string == "=");
		},
		[](std::string const & string, std::vector<expression_t> & expressions) -> expression_t
		{
			if (expressions.size() < 2)
			{
				std::cerr << "ERROR: make_factory: operator_t needs two expressions" << std::endl;
				exit(1); // or throw
			}
			
			auto r = operator_t
			(
				string[0],
				expressions[expressions.size() - 2].release(),
				expressions[expressions.size() - 1].release()
			);
			
			expressions.resize(expressions.size() - 2);
			
			return std::move(r);
		}
	);
	
	return f;
}
Пример #4
0
void ilp_problem_t::add_variables_for_requirement(bool do_maximize)
{
    // ADDING VARIABLES & CONSTRAINTS.
    auto add_req = [this](const pg::requirement_t &req)
    {
        std::string str;
        if (req.conjunction.size() > 1)
        {
            str += "(^";
            for (auto e : req.conjunction)
                str += " " + e.literal.to_string();
            str += ")";
        }
        else
            str += req.conjunction.front().literal.to_string();

        variable_idx_t var = add_variable(
            variable_t(util::format("satisfy:%s", str.c_str()), 0.0));
        constraint_t con(
            util::format("satisfy_req:%s", str.c_str()),
            OPR_GREATER_EQ, 0.0);

        for (auto p : req.conjunction)
        {
            hash_set<variable_idx_t> vars;
            enumerate_variables_for_requirement(p, &vars);
            for (auto v : vars)
                con.add_term(v, 1.0);
        }

        if (not con.terms().empty())
        {
            double b = -1.0 * con.terms().size();
            con.add_term(var, b);
            add_constraint(con);
        }
        else
            add_constancy_of_variable(var, 0.0);

        return var;
    };

    const double PENALTY = do_maximize ? -10000.0 : 10000.0;
    constraint_t con("satisfy_requred_disjunction", OPR_GREATER_EQ, 1.0);
    const std::vector<pg::requirement_t> &reqs = m_graph->requirements();
    bool do_infer_pseudo_positive = phillip()->do_infer_pseudo_positive();

    if (reqs.size() <= 1 and do_infer_pseudo_positive) return;

    bool do_filter = (m_graph->requirements().size() > 1) and do_infer_pseudo_positive;
    for (auto req : m_graph->requirements())
    {
        if (do_filter and not req.is_gold) continue;

        variable_idx_t v = add_req(req);
        con.add_term(v, 1.0);
    }

    if (not con.terms().empty())
    {
        con.add_term(add_variable(variable_t("violation_reqs", PENALTY)), 1.0);
        add_constraint(con);
    }
}
int main(int argc, char** argv) {
  std::cout << "make the image denoising alchemy problem"
            << std::endl;

  std::string model_filename = "image";
  std::string drawing = "sunset";
  std::string corruption = "gaussian";
  std::string smoothing = "square";
  double lambda = 3;
  double sigma = 1;
  size_t rows = 200;
  size_t rings = 7;
  


  

  // Command line parsing
  graphlab::command_line_options clopts("Make the alchemy image", true);
  clopts.attach_option("model", 
                       &model_filename, model_filename,
                       "Alchemy formatted model file");
  clopts.attach_option("drawing", 
                       &drawing, drawing,
                       "drawing type");
  clopts.attach_option("corruption", 
                       &corruption, corruption,
                       "corruption type");
  clopts.attach_option("smoothing", 
                       &smoothing, smoothing,
                       "smoothing type");
  clopts.attach_option("lambda", 
                       &lambda, lambda,
                       "edge parameter");
  clopts.attach_option("sigma", 
                       &sigma, sigma,
                       "noise parameter");
  clopts.attach_option("rows", 
                       &rows, rows,
                       "number of rows and cols");
  clopts.attach_option("rings", 
                       &rings, rings,
                       "number of rings");

  if( !clopts.parse(argc, argv) ) { 
    std::cout << "Error parsing command line arguments!"
              << std::endl;
    return EXIT_FAILURE;
  }


  
  std::cout << "Creating a synethic image." << std::endl;
  image original(rows, rows);
  if(drawing == "sunset") 
    original.paint_sunset(rings);
  else if(drawing == "checkerboard")
    original.paint_checkerboard(rings);
  else {
    std::cout << "Invalid drawing type!" << std::endl;
    exit(1);
  }
  std::cout << "Saving original image. " << std::endl;
  original.save("original.pgm");    

    
  std::cout << "Corrupting Image. " << std::endl;
  image noisy = original;
  if(corruption == "gaussian") 
    noisy.gaussian_corrupt(sigma);
  else if(corruption == "flip")
    noisy.flip_corrupt(rings, 0.75);
  else if(corruption == "ising") 
    noisy = image(rows, rows);
  else {
    std::cout << "Invalid corruption type!" << std::endl;
    exit(1);
  }
  std::cout << "Saving corrupted image. " << std::endl;
  noisy.save("corrupted.pgm");
  

  // dummy variables 0 and 1 and num_rings by num_rings
  std::cout << "Creating edge factor" << std::endl;
  factor_t edge_factor(domain_t(variable_t(0, rings), variable_t(1, rings)));
  // Set the smoothing type
  if(smoothing == "square") {
    edge_factor.set_as_agreement(lambda);
  } else if (smoothing == "laplace") {
    edge_factor.set_as_laplace(lambda);
  } else  {
    std::cout << "Invalid smoothing stype!" << std::endl;
    assert(false);
  }
  std::cout << edge_factor << std::endl;
  
  std::cout << "Constructing factor graph." << std::endl;
  factorized_model model;
  // Add all the node factors
  double sigmaSq = sigma*sigma;
  for(size_t i = 0; i < noisy.rows(); ++i) {
    for(size_t j = 0; j < noisy.cols(); ++j) {
      // initialize the potential and belief
      uint32_t pixel_id = noisy.vertid(i, j);
      variable_t var(pixel_id, rings);
      factor_t factor(var);
      // Set the node potential
      double obs = noisy.pixel(i, j);
      if(corruption == "gaussian") {
        for(size_t pred = 0; pred < rings; ++pred) {
          factor.logP(pred) = 
            -(obs - pred)*(obs - pred) / (2.0 * sigmaSq);
        }
      } else if(corruption == "flip") {
        for(size_t pred = 0; pred < rings; ++pred) {
          factor.logP(pred) = obs == pred? 0 : -sigma;
        }
      } else if(corruption == "ising") {
        // Do nothing since we want a uniform node potential
        factor.uniform();
      } else {
        std::cout << "Invalid corruption!" << std::endl;
        exit(1);
      }
      factor.normalize();
      model.add_factor(factor);
    } // end of for j in cols
  } // end of for i in rows

  // Construct edge_factors  
  for(size_t i = 0; i < noisy.rows(); ++i) {
    for(size_t j = 0; j < noisy.cols(); ++j) {
      size_t source = noisy.vertid(i,j);
      variable_t source_var(source, rings);
      if(i+1 < noisy.rows()) {
        vertex_id_t target = noisy.vertid(i+1, j);
        variable_t target_var(target, rings);
        domain_t dom(source_var, target_var);
        edge_factor.set_args(dom);
        model.add_factor(edge_factor);
      }
      if(j+1 < noisy.cols()) {
        vertex_id_t target = noisy.vertid(i, j+1);
        variable_t target_var(target, rings);
        domain_t dom(source_var, target_var);
        edge_factor.set_args(dom);
        model.add_factor(edge_factor);
      }
    } // end of for j in cols
  } // end of for i in rows

  std::cout << "Saving model in alchemy format" << std::endl;
  model.save_alchemy(model_filename + ".alchemy");


  return EXIT_SUCCESS;
} // end of main