pyab_experiment.data_structures.syntax_tree

Contents

pyab_experiment.data_structures.syntax_tree#

Module that houses the abstract syntax tree (AST) representation of an experiment It’s a collection of pydantic classes that represent a tree with several specialized nodes each representing a specific data structure of the experiment

Module Contents#

Classes#

BooleanOperatorEnum

Enum representing the boolean operators that can be used in a

ConditionalType

Enum representing the types of conditionals that can be used in an experiment.

ExperimentAST

A model representing the abstract syntax tree (AST) of an experiment.

ExperimentConditional

A model representing a conditional (if then else) in an experiment.

ExperimentGroup

A group definition for an experiment. A group in an experiment

Identifier

A model representing an identifier. (i.e a variable or function name)

LogicalOperatorEnum

Enum representing the logical operators that can be used in a terminal predicate.

RecursivePredicate

A model representing a recursive predicate.

TerminalPredicate

A model representing a terminal predicate. A terminal predicate

class pyab_experiment.data_structures.syntax_tree.BooleanOperatorEnum[source]#

Bases: enum.Enum

Enum representing the boolean operators that can be used in a recursive predicate, effectively chaining complex predicates. e.g. (predicate1 OR predicate2) AND NOT predicate3

AND[source]#
NOT[source]#
OR[source]#
class pyab_experiment.data_structures.syntax_tree.ConditionalType[source]#

Bases: enum.Enum

Enum representing the types of conditionals that can be used in an experiment. These are the classical if then else keywoods found in traditional programming languages

ELIF[source]#
ELSE[source]#
IF[source]#
class pyab_experiment.data_structures.syntax_tree.ExperimentAST[source]#

Bases: pydantic.BaseModel

A model representing the abstract syntax tree (AST) of an experiment.

id[source]#

The ID of the experiment.

Type:

str

splitting_fields[source]#

The fields used for splitting groups.

Type:

List[str] | None

salt[source]#

The salt used change hashing. Useful in case multiple experiments with the same splitting fields are used.

Type:

str | None

conditions[source]#

The conditions used in the experiment.

Type:

Union[ExperimentConditional, List[ExperimentGroup]]

conditions: ExperimentConditional | list[ExperimentGroup][source]#
id: str[source]#
salt: str | None[source]#
splitting_fields: list[str] | None[source]#
class pyab_experiment.data_structures.syntax_tree.ExperimentConditional[source]#

Bases: pydantic.BaseModel

A model representing a conditional (if then else) in an experiment.

conditional_type[source]#

The type of conditional - either IF, ELSE IF, or ELSE)

Type:

ConditionalType

predicate[source]#

The (possibly recursive) predicate used in the conditional.

Type:

Union[TerminalPredicate, RecursivePredicate, None]

true_branch[source]#

The true branch of the conditional. could be a group (terminal) or nested conditional. For example IF p1{ IF (p2){…}}. Semantically represents the branch to explore if the predicate evaluates to TRUE

Type:

Union[list[ExperimentGroup], “ExperimentConditional”]

false_branch[source]#

The false branch of the conditional (if any) same as above, but semantically representing the branch to explore if the predicate is FALSE. Note that it may be None, for ex on a clause “IF p1{ branch1 }” if the predicate p1 is false there is no branch to explore

Type:

Union[list[ExperimentGroup], “ExperimentConditional”, None]

conditional_type: ConditionalType[source]#
false_branch: list[ExperimentGroup] | ExperimentConditional | None[source]#
predicate: TerminalPredicate | RecursivePredicate | None[source]#
true_branch: list[ExperimentGroup] | ExperimentConditional[source]#
class pyab_experiment.data_structures.syntax_tree.ExperimentGroup[source]#

Bases: pydantic.BaseModel

A group definition for an experiment. A group in an experiment (or element of a group) is a string associated with a weight The weight represents the likelyhood of choosing the element.

For example with 2 groups A,B with weights 1,2 respectively. B is twice as likely to be chosen compared to A. Effectively the probability of choosing A becomes 1/3, while P(choosing B) becomes 2/3

group_definition[source]#

The definition of the group.

Type:

str

group_weight[source]#

The weight of the group.

Type:

Union[NonNegativeFloat, NonNegativeInt]

class Config[source]#
smart_union = True[source]#
group_definition: int | float | str[source]#
group_weight: pydantic.NonNegativeFloat | pydantic.NonNegativeInt[source]#
class pyab_experiment.data_structures.syntax_tree.Identifier[source]#

Bases: pydantic.BaseModel

A model representing an identifier. (i.e a variable or function name)

name[source]#

The name of the identifier.

Type:

str

name: str[source]#
class pyab_experiment.data_structures.syntax_tree.LogicalOperatorEnum[source]#

Bases: enum.Enum

Enum representing the logical operators that can be used in a terminal predicate.

EQ[source]#
GE[source]#
GT[source]#
IN[source]#
LE[source]#
LT[source]#
NE[source]#
NOT_IN[source]#
class pyab_experiment.data_structures.syntax_tree.RecursivePredicate[source]#

Bases: pydantic.BaseModel

A model representing a recursive predicate. Similar to terminal predicates, but chains recursive definitions with logical operators.

e.g. in predicate1 AND predicate2 predicate1 is the left term AND is the logical operator predicate2 is the right term

left_predicate[source]#

The left predicate of the recursive predicate.

Type:

Union[TerminalPredicate, “RecursivePredicate”]

boolean_operator[source]#

The boolean operator used in the recursive predicate.

Type:

BooleanOperatorEnum

right_predicate[source]#

The right predicate of the recursive predicate.

Type:

Union[TerminalPredicate, “RecursivePredicate”, None]

boolean_operator: BooleanOperatorEnum[source]#
left_predicate: TerminalPredicate | RecursivePredicate[source]#
right_predicate: TerminalPredicate | RecursivePredicate | None[source]#
class pyab_experiment.data_structures.syntax_tree.TerminalPredicate[source]#

Bases: pydantic.BaseModel

A model representing a terminal predicate. A terminal predicate typically consists of 2 terms (either literals, or identifiers) and a boolean operand between them.

for example in the predicate my_int_variable >= 2, we have my_variable: - the left term “>=” the operand “2” - the right term (int literal with value 2)

left_term[source]#

The left term of the predicate.

Type:

Union[float, int, str, tuple, Identifier]

logical_operator[source]#

The logical operator used in the predicate.

Type:

LogicalOperatorEnum

right_term[source]#

The right term of the predicate.

Type:

Union[float, int, str, tuple, Identifier]

left_term: float | int | str | tuple | Identifier[source]#
logical_operator: LogicalOperatorEnum[source]#
right_term: float | int | str | tuple | Identifier[source]#