

def free_variables(*terms, **kwargs):
    '\n    Returns a frozenset of variables free in given terms.\n\n    kwargs: by_name , False by default.\n    If by_name=True, the result is a set of variable names, and\n    binding occurs by name. Otherwise, the result is a set of Var\n    objects, and ForAll X:s1 does not bind X:s2.\n    '
    by_name = kwargs.get('by_name', False)
    _free_variables = partial(free_variables, by_name=by_name)
    t = (terms[0] if (len(terms) == 1) else terms)
    if (type(t) is Var):
        return frozenset(((t.name if by_name else t),))
    elif (type(t) in (tuple, Const, Apply, Eq, Ite, Not, And, Or, Implies, Iff)):
        return union(*(_free_variables(x) for x in t))
    elif (type(t) in (ForAll, Exists)):
        return (_free_variables(t.body) - _free_variables(*t.variables))
    elif hasattr(t, 'args'):
        return union(*(_free_variables(x) for x in t.args))
    else:
        assert False, type(t)

dataset/ETHPy150Open Microsoft/ivy/ivy/logic_util.py free_variables/original