All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.aksw.jena_sparql_api.views.VarBinding Maven / Gradle / Ivy

The newest version!
package org.aksw.jena_sparql_api.views;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

import org.aksw.commons.collections.multimaps.BiHashMultimap;
import org.aksw.commons.collections.multimaps.IBiSetMultimap;
import org.aksw.jena_sparql_api.utils.QuadUtils;
import org.apache.jena.graph.Node;
import org.apache.jena.sparql.core.Quad;
import org.apache.jena.sparql.core.Var;


class BindingVal
    extends VarConst
{
    public BindingVal() {
        super();
    }

    public BindingVal(Set keys, Node value) {
        super(keys, value);
    }
}



/**
 * A variable binding maps query vars to sets of view variables.
 *
 *
 *
 *
 * @author Claus Stadler 
 *
 */
public class VarBinding {
    private Map keyToToken = new HashMap();
    private Map valueToToken = new HashMap();
    private Map tokenToSet = new HashMap();
    //private Map tokenToValue = new HashMap();

    private int nextToken;

    public VarBinding() {
    }

    public Map getQueryVarToConstant() {
        Map result = new HashMap();

        for(Entry entry : keyToToken.entrySet()) {
            Var value = entry.getKey();
            Integer token = entry.getValue();

            BindingVal val = tokenToSet.get(token);
            Node constant = val.getValue();
            result.put(value, constant);
        }

        return result;
    }

    public IBiSetMultimap getQueryVarToViewVars() {
        IBiSetMultimap result = new BiHashMultimap();

        for(Entry entry : keyToToken.entrySet()) {
            Var value = entry.getKey();
            Integer token = entry.getValue();

            BindingVal val = tokenToSet.get(token);
            Set keys = val.getKeys();
            result.putAll(value, keys);
        }

        return result;
    }

    /*
     * Return a mapping from view to query vars
     *
     */
    public IBiSetMultimap getViewVarToQueryVars() {
        IBiSetMultimap tmp = getQueryVarToViewVars();
        IBiSetMultimap result = tmp.getInverse();

        return result;

        /*
        Multimap result = HashMultimap.create();

        for(Entry entry : valueToToken.entrySet()) {
            Var value = entry.getKey();
            Integer token = entry.getValue();

            BindingVal val = tokenToSet.get(token);
            Set keys = val.getKeys();
            result.putAll(value, keys);
        }

        return result;
        */
    }

    public Set getQueryVars() {
        return keyToToken.keySet();
    }

    public Set getViewVars(Var queryVar) {
        BindingVal tmp = get(queryVar);
        if(tmp == null) {
            return null;
        }

        return tmp.getKeys();
    }

    public Node getConstant(Var queryVar) {
        BindingVal tmp = get(queryVar);
        if(tmp == null) {
            return null;
        }

        return tmp.getValue();
    }


    public BindingVal get(Var queryVar) {
        Integer token = keyToToken.get(queryVar);

        if(token == null) {
            return null;
        }

        BindingVal result = tokenToSet.get(token);

        return result;
    }

    /*
    public VarBinding(IBiSetMultimap queryVarToViewVars) {
        this.queryVarToViewVars = queryVarToViewVars;
    }
    */

    /*
    public boolean putAll(VarBinding other) {
        for(other.ge)
    }
    */

    public boolean put(Var queryVar, Var viewVar) {
        Integer keyToken = keyToToken.get(queryVar);
        Integer valueToken = valueToToken.get(viewVar);


        if(valueToken == null) {
            if(keyToken == null) {
                Integer token = nextToken++;

                valueToToken.put(viewVar, token);
                keyToToken.put(queryVar, token);

                BindingVal val = new BindingVal();
                val.getKeys().add(viewVar);

                tokenToSet.put(token, val);
            } else {

                // The value already exists - point the key to the token
                valueToToken.put(viewVar, keyToken);

                BindingVal val = tokenToSet.get(keyToken);

                val.getKeys().add(viewVar);
            }
        } else {
            if(keyToken == null) {

                // The value exists, but has not yet been associated with the key
                keyToToken.put(queryVar, valueToken);


            } else {

                if(keyToken.equals(valueToken)) {
                    return true;
                }

                // Merge both the key and value token things
                BindingVal a = tokenToSet.get(keyToken);
                BindingVal b = tokenToSet.get(valueToken);

                Node valA = a.getValue();
                Node valB = b.getValue();

                Node res = valA == null ? valB : valB;

                if(valB != null && valB != res) {
                    return false;
                }

                a.setValue(res);

                for(Var vv : b.getKeys()) {
                    valueToToken.put(vv, keyToken);
                }

                tokenToSet.remove(valueToken);
                a.getKeys().addAll(b.getKeys());
            }
        }

        return true;
    }


    public boolean put(Var queryVar, Node node) {
        if(node == null) {
            return true;
        } else if(node.isVariable()) {
            return put(queryVar, (Var)node);
        }

        Integer token = keyToToken.get(queryVar);

        if(token == null) {
            token = nextToken++;

            keyToToken.put(queryVar, token);

            BindingVal val = new BindingVal();
            tokenToSet.put(token, val);

            val.setValue(node);

            return true;
        } else {
            BindingVal val = tokenToSet.get(token);
            Node existing = val.getValue();
            if(existing == null) {
                val.setValue(node);
                return true;
            } else if(existing.equals(node)) {
                return true;
            } else {
                return false;
            }
        }
    }


    public void putAll(VarBinding that) {
        for(Entry entry : that.getQueryVarToViewVars().entries()) {
            this.put(entry.getKey(), entry.getValue());
        }

        for(Entry entry : that.getQueryVarToConstant().entrySet()) {
            this.put(entry.getKey(), entry.getValue());
        }
    }


    public static VarBinding create(Quad a, Quad b)
    {
        VarBinding result = new VarBinding();

        List nAs = QuadUtils.quadToList(a);
        List nBs = QuadUtils.quadToList(b);

        for(int i = 0; i < 4; ++i) {
            Var nA = (Var)nAs.get(i);
            Node nB = nBs.get(i);

            if(!result.put(nA, nB)) {
                return null;
            }
        }

        return result;
    }


    @Override
    public String toString() {
        String result = "{";
        boolean isFirst = true;
        for(Entry entry : keyToToken.entrySet()) {
            Var key = entry.getKey();
            Integer token = entry.getValue();
            BindingVal val = tokenToSet.get(token);

            if(isFirst) {
                isFirst = false;
            } else {
                result += ", ";
            }

            result += key + ": (" + token + ")" + val;
        }
        result += "}";
        return result;

        //return "keyToToken: " + keyToToken + ", tokenToSet:" + tokenToSet;
    }



    /*
    public Set getQueryVars() {
        return queryVarToViewVars.asMap().keySet();
    }

    public Set get(Var queryVar) {
        return queryVarToViewVars.get(queryVar);
    }


    public IBiSetMultimap getMap()
    {
        return queryVarToViewVars;
    }


    public VarBinding computeClosure() {
        Map> state = new HashMap>();

        // Invert the binding: For the set of viewVars, get the set of queryVars that map to them
        IBiSetMultimap viewVarsToQueryVars = queryVarToViewVars.getInverse();


        for(Entry> entry : queryVarToViewVars.asMap().entrySet()) {
            Var queryVar = entry.getKey(); //open.iterator().next();
            Collection viewVars = entry.getValue();

            // Re-use a corresponding viewVar-set
            // in the state, otherwise create a new one
            Set mergedViewVars = state.get(queryVar);
            if(mergedViewVars == null) {
                mergedViewVars = new HashSet(viewVars);
            }

            for(Var viewVar : viewVars) {
                Set queryVarsB = viewVarsToQueryVars.get(viewVar);

                for(Var queryVarB : queryVarsB) {
                    if(queryVarB.equals(queryVar)) {
                        continue;
                    }

                    Set viewVarsC = state.get(queryVarB);
                    // A viewVars set might not exist for a key yet
                    if(viewVarsC == null) {
                        viewVarsC = queryVarToViewVars.get(queryVarB);
                    }

                    mergedViewVars.addAll(viewVarsC);

                    state.put(queryVarB, mergedViewVars);
                }
            }
        }

        // OPTIMIZE: Use some batch function for this - or at least hide the complexity here
        IBiSetMultimap map = new BiHashMultimap();
        for(Entry> entry : state.entrySet()) {
            Var queryVar = entry.getKey();

            for(Var viewVar : entry.getValue()) {
                map.put(queryVar, viewVar);
            }

        }

        VarBinding result = new VarBinding(map);

        return result;
    }


//	public static  Set getAll(Collection keys, IBiSetMultimap map) {
//		Set result
//	}



    /*

    public Set getEquivalences(Var key, boolean reflexiv)
    {
        Set result = MultimapUtils.transitiveGetBoth(queryVarToViewVars, key);
        if(reflexiv) {
            result.add(key);
        }

        return result;
    }

    public Set getAllEquivalences(Collection keys, boolean reflexiv)
    {
        Set result = new HashSet();

        Set open = new HashSet(keys);
        while(!open.isEmpty()) {
            Var key = open.iterator().next();
            open.remove(key);

            Set equivs = getEquivalences(key, reflexiv);
            open.removeAll(equivs);

            result.addAll(equivs);
        }

        return result;
    }

    * /

    @Override
    public String toString() {
        return "" + queryVarToViewVars;
    }

    @Override
    public int hashCode() {
        final int prime = 31;
        int result = 1;
        result = prime
                * result
                + ((queryVarToViewVars == null) ? 0 : queryVarToViewVars
                        .hashCode());
        return result;
    }

    @Override
    public boolean equals(Object obj) {
        if (this == obj)
            return true;
        if (obj == null)
            return false;
        if (getClass() != obj.getClass())
            return false;
        VarBinding other = (VarBinding) obj;
        if (queryVarToViewVars == null) {
            if (other.queryVarToViewVars != null)
                return false;
        } else if (!queryVarToViewVars.equals(other.queryVarToViewVars))
            return false;
        return true;
    }
    */
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy