def __count_exclusions(self, num): from sweetpea.constraints import Exclude excluded_crossings = set() excluded_external_names = set() # Get the exclude constraints. exclusions = list( filter(lambda c: isinstance(c, Exclude), self.constraints)) if not exclusions: return 0 # If there are any, generate the full crossing as a list of tuples. levels_lists = [list(f.levels) for f in self.crossing[0]] all_crossings = list(product(*levels_lists)) for constraint in exclusions: if constraint.factor.has_complex_window(): # If the excluded factor has a complex window, then we don't need # to reduce the sequence length. What if the transition being excluded # is in the crossing? If it is, then they shouldn't be excluding it. # We should give an error if we detect that. continue # Retrieve the derivation function that defines this exclusion. excluded_level = constraint.level if type(excluded_level) is SimpleLevel: for c in all_crossings: if excluded_level in c: excluded_crossings.add( get_internal_level_name(c[0]) + ", " + get_internal_level_name(c[1])) else: # For each crossing, ensure that atleast one combination is possible with the disgn-only factors keeping in mind the exclude contraints. for c in all_crossings: if all( list( map( lambda d: self.__excluded_derived( excluded_level, c + d), list( product(*[ list(f.levels) for f in filter( lambda f: f not in self. crossing[0], self.design) ]))))): excluded_crossings.add( get_internal_level_name(c[0]) + ", " + get_internal_level_name(c[1])) excluded_external_names.add( get_external_level_name(c[0]) + ", " + get_external_level_name(c[1])) if self.require_complete_crossing and len(excluded_crossings) != 0: er = "Complete crossing is not possible beacuse the following combinations have been excluded:" for names in excluded_external_names: er += "\n" + names self.errors.add(er) return len(excluded_crossings)
def validate_factor_and_level(block: Block, factor: Factor, level: Union[SimpleLevel, DerivedLevel]) -> None: if not block.has_factor(factor): raise ValueError(("A factor with name '{}' wasn't found in the design. " +\ "Are you sure the factor was included, and that the name is spelled " +\ "correctly?").format(factor.factor_name)) if not factor.has_level(level): raise ValueError(("A level with name '{}' wasn't found in the '{}' factor, " +\ "Are you sure the level name is spelled correctly?").format(get_internal_level_name(level), factor.factor_name))
def get_all_internal_level_names( design: List[Factor]) -> List[Tuple[str, str]]: return [(factor.factor_name, get_internal_level_name(level)) for factor in design for level in factor.levels]