def parse(obj, required_properties=None, additional_properties=None,
          ignore_optional_property_errors=None):
    if not (required_properties is
            additional_properties is
            ignore_optional_property_errors is None):
        with parsing(required_properties=required_properties,
                     additional_properties=additional_properties,
                     ignore_optional_property_errors=ignore_optional_property_errors):
            return parse(obj)
    validator = None
    if isinstance(obj, Validator):
        validator = obj
    elif inspect.isclass(obj) and issubclass(obj, Validator):
        validator = obj()
    else:
        try:
            validator = _NAMED_VALIDATORS[obj]
        except (KeyError, TypeError):
            for factory in _VALIDATOR_FACTORIES:
                validator = factory(obj)
                if validator is not None:
                    break
        else:
            if inspect.isclass(validator) and issubclass(validator, Validator):
                _NAMED_VALIDATORS[obj] = validator = validator()
    if not isinstance(validator, Validator):
        raise SchemaError("%r cannot be parsed as a Validator" % obj)
    return validator