Ejemplo n.º 1
0
Alist_t<Abinop_t> Ajoin_t::Clones (Alognode_t *leftinput, 
				   Alognode_t *rightinput)
{
  Alist_t<Abinop_t> clones;

  if (Aglob_vars()->oopt->left_deep_only &&
      rightinput->GetOp ()->GetNumber () != Aget)
    return clones;		// left deep only.

  if (Aglob_vars()->oopt->right_deep_only &&
      leftinput->GetOp ()->GetNumber () != Aget)
    return clones;		// right deep only.


  Aset_t<Aptree_t> leftoprns = leftinput->GetLogProps ()->operations ();
  leftoprns.Minus (leftinput->GetLogProps ()->need_unnesting ());

  Aset_t<Aptree_t> rightoprns = rightinput->GetLogProps ()->operations ();
  rightoprns.Minus (rightinput->GetLogProps ()->need_unnesting ());

  Aset_t<Aptree_t> tupleref_ops = Aglob_vars()->query->tupleref_ops ();
  Aset_t<Aptree_t> &relref_ops = 
    (Aset_t<Aptree_t> &)Aglob_vars()->query->relref_ops ();
				// converting a const to a non-const.
				// will fix this later.

//  Aset_t<Aptree_t> oprns_intersect = leftoprns;
//  oprns_intersect.Intersect (rightoprns);
//  oprns_intersect.Delete (&Aptree_t::null_pred_tree ());
  
//  if (Adont_explore (oprns_intersect))
//    return clones;		// not joinable.
//
// this need not be checked here because the
// Ajoin_t::Apply function does not send us any that dont
// satisfy this...

  tupleref_ops.Intersect (relref_ops);
				// we are interested only in those
				// tuple ref operations which represent
				// real extents.
  tupleref_ops.Intersect (leftoprns);
  tupleref_ops.Intersect (rightoprns);
				// now tupleref_ops constains those
				// tupleref operations which are present
				// in both inputs and which represent
				// real extents.

  // now we have a set of tupleref operation each of which signifies
  // a legal pointer-based join of the two inputs.
  // now we start looking for other (normal) join operations.

  Aset_t<Aptree_t> join_ops = Aglob_vars()->query->join_ops ();
  join_ops.Minus (leftoprns);
  join_ops.Minus (rightoprns); // now join_ops contains the join ops
				// which havent yet been applied.

  for (int eos = join_ops.StartTraversal ();
       !eos;
	)
    {
      Aptree_t *oprn = join_ops.CurrentElement ();
      
      // this is a join operation only if one of its operands
      // is present in the left input and the other is
      // present in the right input.
      int left_present_in_left = 
	leftoprns.HasElement (oprn->arg (0)) ? 1 : 0;
      int left_present_in_right = 
	rightoprns.HasElement (oprn->arg (0)) ? 1 : 0;
      int right_present_in_left = 
	leftoprns.HasElement (oprn->arg (1)) ? 1 : 0;
      int right_present_in_right = 
	rightoprns.HasElement (oprn->arg (1)) ? 1 : 0;

      if (left_present_in_left + left_present_in_right == 1 &&
	  right_present_in_left + right_present_in_right == 1)
	eos = join_ops.Advance ();
      else
	eos = join_ops.DeleteAndAdvance ();	
				// if this doesnt satisfy, then delete it.
    }

  if (Aglob_vars()->oopt->do_mat_to_join)
    join_ops.Union (tupleref_ops);
				// now join_ops contains all the
				// join operations.

  FOR_EACH_ELEMENT_OF_SET (join_ops)
    {
      Aptree_t *oprn = join_ops.CurrentElement ();

      Ajoin_t *newjoin = (Ajoin_t *)Duplicate ();
      newjoin->_operations.Insert (oprn);

      newjoin->_undone_tuplerefs = tupleref_ops;
      newjoin->_undone_tuplerefs.Delete (oprn);
				// tuplerefs which have to be done
				// but which haven't yet been done...
      clones.Insert (newjoin);

      // see if we can do a join using an inverse link...
      if (Aglob_vars()->oopt->do_inverse_links &&
	  oprn->is_tupleref ())
	{
	  Acat_t::attrid_t tupleref_attrid = 
	    ((Atupleref_t *)oprn->func ())->attrid ();
	  if (Aglob_vars()->cat->has_inverse (tupleref_attrid))
	    {
	      Ajoin_t *inverse_newjoin = (Ajoin_t *)Duplicate ();
	      inverse_newjoin->_operations.Insert (oprn);
	      inverse_newjoin->_undone_tuplerefs = 
		newjoin->_undone_tuplerefs;
	      inverse_newjoin->_inverse = 1;
	      clones.Insert (inverse_newjoin);
	    }
	}
    }

  return clones;
}
Ejemplo n.º 2
0
ON_Hatch* ON_Hatch::DuplicateHatch() const
{
  return Duplicate();
}
Ejemplo n.º 3
0
_HYEvent::_HYEvent(_HYEvent& he)
{
    Duplicate (&he);
}