예제 #1
0
def test_disjunction():
    rows = [
        ["Tiger", "animal"],
        ["Abe", "man"],
        ["Bob", "man"],
        ["Abby", "woman"],
        ["Beatrice", "woman"],
    ]
    a_df = pd.DataFrame(rows, columns=["name", "species"])
    exp_rows = ["Abe", "Bob", "Abby", "Beatrice"]
    exp_df = pd.DataFrame(exp_rows, columns=["X"])
    d = db(a_df)

    base_rules = [
        R.man(X) << row(name=X, species="man"),
        R.woman(X) << row(name=X, species="woman"),
    ]
    rules = [
        R.human(X) << R.man(X),
        R.human(X) << R.woman(X),
    ]
    query = [R.human(X)]
    humans = d(base_rules + rules + query)
    assert_df(humans.df(), exp_df)

    # Or Clause
    or_rules = [R.human(X) << or_(R.man(X), R.woman(X))]
    humans_or = d(base_rules + or_rules + query)
    assert_df(humans_or.df(), exp_df)
예제 #2
0
def test_user_api_filter():
    rows = [["Abe", "M"], ["Bob", "M"], ["Abby", "F"]]
    a_df = pd.DataFrame(rows, columns=["name", "gender"])
    exp_df = pd.DataFrame(["Abe", "Bob"], columns=["X"])

    ds = db(a_df)
    # select males
    males = ds([row(name=X, gender="M")])
    assert_df(males.df(), exp_df)
예제 #3
0
def test_single_body_rule():
    X = V.X
    rows = [["Abe", "man"], ["Bob", "man"], ["Samba", "animal"]]
    a_df = pd.DataFrame(rows, columns=["name", "species"])
    exp_df = pd.DataFrame(["Abe", "Bob"], columns=["X"])

    # Then
    ds = db(a_df)
    man = R.man(X) << row(name=X, species="man")
    human = ds([man, R.man(X)])
    assert_df(human.df(), exp_df)
예제 #4
0
def test_facts_from_rules():
    # Normally, we pass facts through a dataframe. But sometimes, a fact may just be needed to assert something
    # about the context/environment. So we pass that in the rules section
    exp_data = [["adam"]]
    exp_df = pd.DataFrame(data=exp_data, columns=["X"])
    rules = [
        R.father("adam", "kane"),  # This is the global fact or assertion
        R.parent(V.X, V.Parent) << R.father(V.X, V.Parent),
        R.parent(V.X, "kane"),
    ]
    ds = db()
    result = ds(rules)
    assert_df(result.df(), exp_df)
예제 #5
0
def test_conjunction():
    man = lambda person: [person, "AA", "man"]
    woman = lambda person: [person, "AA", "woman"]
    X = V.X
    Y = V.Y
    Z = V.Z

    rows = [
        _parent("Abe", "Bob"),  # Abe is a parent of Bob
        _parent("Abby", "Bob"),
        _parent("Bob", "Carl"),
        _parent("Bob", "Connor"),
        _parent("Beatrice", "Carl"),
        man("Abe"),
        man("Bob"),
        woman("Abby"),
        woman("Beatrice"),
    ]
    a_df = pd.DataFrame(rows, columns=PEOPLE_COLUMNS)
    exp_df = pd.DataFrame([["Abe", "Bob"], ["Bob", "Carl"], ["Bob", "Connor"]],
                          columns=["X", "Y"])

    # Then test binary conjunction
    d = db(a_df)
    rules = [
        R.man(X) << row(name=X, rel="man"),
        R.parent(X, Y) << row(name=X, name2=Y, rel="parent"),
        R.father(X, Y) << and_(R.man(X), R.parent(X, Y)),
    ]
    queries = rules + [R.father(X, Y)]
    fathers = d(queries)
    assert_df(fathers.df(), exp_df)

    # Test n-ary conjunction
    grandfather_rule = R.grandfather(X, Y) << and_(R.man(X), R.parent(X, Z),
                                                   R.parent(Z, Y))
    rules = rules + [grandfather_rule]
    gf_d = d(rules + [R.grandfather(X, Y)])
    gf_rows = [["Abe", "Carl"], ["Abe", "Connor"]]
    exp_gf_df = pd.DataFrame(gf_rows, columns=["X", "Y"])
    assert_df(gf_d.df(), exp_gf_df)
예제 #6
0
def test_recursion():
    database = [
        _parent("A", "B"),
        _parent("B", "C"),
        _parent("C", "D"),
        _parent("AA", "BB"),
        _parent("BB", "CC"),
    ]
    df = pd.DataFrame(database, columns=PEOPLE_COLUMNS)
    base = [
        R.parent(X, Y) << row(name=X, name2=Y, rel="parent"),
    ]
    rules = [
        R.ancestor(X, Y) << R.parent(X, Y),
        R.ancestor(X, Z) << and_(R.parent(X, Y), R.ancestor(Y, Z)),
    ]
    """
    or 
    rules = [
        R.ancestor(X,Y) << or_(R.parent(X,Y),
                               and_(R.parent(X, Z),
                                    R.parent(Z, Y)))
    ]
    """

    query = R.ancestor(X, Y)

    d = db(df)
    all_rules = base + rules
    exp_d = d(all_rules + [query])

    A = "A"
    B = "B"
    C = "C"
    D = "D"
    AA = "AA"
    BB = "BB"
    CC = "CC"
    exp_rows = [
        [A, B],
        [B, C],
        [C, D],
        [AA, BB],
        [BB, CC],
        [A, C],
        [B, D],
        [AA, CC],
        [A, D],
    ]
    expected_result = pd.DataFrame(exp_rows, columns=["X", "Y"])

    assert_df(exp_d.df(), expected_result)

    new_rule = R.main(X, Y) << and_(R.ancestor(X, Y), eq(X, "AA"), eq(Y, "C"))

    d2 = d(all_rules + [new_rule] + [R.main(X, Y)])
    assert_df(d2.df(), a_df({}))
    d3 = d(all_rules + [R.ancestor(X, "C")])
    assert_df(d3.df(), a_df({"X": ["A", "B"]}))
    d4 = d(all_rules + [R.ancestor("AA", X)])
    assert_df(d4.df(), a_df({"X": ["BB", "CC"]}))
    rules = rules + [
        R.intermediate(Z, X, Y) << and_(R.ancestor(X, Z), R.ancestor(Z, Y))
    ]
    d5 = d(base + rules + [R.intermediate(Z, "A", "D")])
    assert_df(d5.df(), a_df({"Z": ["B", "C"]}))