def evaluate(self):
     # evaluate child node
     eval_input = self.input.evaluate()
     new_relation = Relation("Result", self.get_schema())
     # add all existing tuples
     for tup in eval_input.tuples:
         new_relation.add_tuple(tup)
     return new_relation
 def evaluate(self):
     """Performs the renaming."""
     # evaluate child node
     eval_input = self.input.evaluate()
     new_relation = Relation(self.name, self.get_schema())
     # add all existing tuples
     for tup in eval_input.tuples:
         new_relation.add_tuple(tup)
     return new_relation
    def evaluate(self):
        """Performs a set operation on its inputs."""
        # evaluate child nodes
        l_eval_input = self.l_input.evaluate()
        r_eval_input = self.r_input.evaluate()

        new_relation = Relation("Result", self.get_schema())
        # add tuples to new relation
        for tup in self.operator(l_eval_input.tuples, r_eval_input.tuples):
            new_relation.add_tuple(tup)
        return new_relation
    def evaluate(self):
        """Performs a cartesian product on its inputs."""
        # evaluate child nodes
        l_eval_input = self.l_input.evaluate()
        r_eval_input = self.r_input.evaluate()

        new_relation = Relation("Result", self.get_schema())
        # insert cartesian product of tuples
        for tup1 in l_eval_input.tuples:
            for tup2 in r_eval_input.tuples:
                new_relation.add_tuple(tup1 + tup2)
        return new_relation
 def evaluate(self):
     """Performs grouping and aggregation on its inputs."""
     # evaluate input
     eval_input = self.input.evaluate()
     # build groups
     groups = self._build_groups(eval_input)
     # compute aggregations
     tuples = self._compute_aggregations(eval_input, groups)
     # build new relation
     new_relation = Relation("Result", self.get_schema())
     # insert tuples into relation
     for tup in tuples:
         new_relation.add_tuple(tup)
     return new_relation
    def evaluate(self):
        """Performs the selection by evaluating the predicate on its input."""
        # evaluate child node
        eval_input = self.input.evaluate()

        # build empty relation with same schema as input
        new_relation = Relation("Result", self.get_schema())
        # check predicate for each tuple in input
        for tup in eval_input.tuples:
            # evaluate predicate for given tup using eval
            if eval(self.predicate,
                    Selection._locals_dict(tup, eval_input.attributes)):
                new_relation.add_tuple(
                    tup)  # implicitly handles duplicate elimination
        return new_relation
    def evaluate(self):
        """Performs the projection."""
        # evaluate child node
        eval_input = self.input.evaluate()

        # build new empty relation with the projected attributes
        new_relation = Relation("Result", self.get_schema())

        # add tuples to new relation
        attr_indexes = [*map(eval_input.get_attribute_index, self.attributes)]
        for tup in eval_input.tuples:
            new_tup = tuple(tup[i] for i in attr_indexes)
            new_relation.add_tuple(
                new_tup)  # automatically eliminates duplicates
        return new_relation
    def evaluate(self):
        """Performs a theta join on its inputs."""
        # evaluate child nodes
        l_eval_input = self.l_input.evaluate()
        r_eval_input = self.r_input.evaluate()

        new_relation = Relation("Result", self.get_schema())
        # insert cartesian product of tuples
        for tup1 in l_eval_input.tuples:
            for tup2 in r_eval_input.tuples:
                potential_tup = tup1 + tup2
                if eval(
                        self.theta,
                        Selection._locals_dict(potential_tup,
                                               new_relation.attributes)):
                    new_relation.add_tuple(
                        potential_tup
                    )  # implicitly handles duplicate elimination
        return new_relation
    def evaluate(self):
        """Performs the selection by evaluating the predicate on its input,
           which must be a relation containing an index on the selected predicate.

        Note:
            Currently, this access method does not use the index, but performs the access via scan.
        """
        # evaluate child node
        eval_input = self.input.evaluate()

        # build empty relation with same schema as input
        new_relation = Relation("Result", self.get_schema())
        # check predicate for each tuple in input
        for tup in eval_input.tuples:
            # evaluate predicate for given tup using eval
            if eval(self.predicate,
                    Selection._locals_dict(tup, eval_input.attributes)):
                new_relation.add_tuple(
                    tup)  # implicitly handles duplicate elimination
        return new_relation