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

org.linqs.psl.runtime.Runtime Maven / Gradle / Ivy

/*
 * This file is part of the PSL software.
 * Copyright 2011-2015 University of Maryland
 * Copyright 2013-2023 The Regents of the University of California
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.linqs.psl.runtime;

import org.linqs.psl.application.inference.InferenceApplication;
import org.linqs.psl.application.learning.weight.WeightLearningApplication;
import org.linqs.psl.config.Config;
import org.linqs.psl.config.Option;
import org.linqs.psl.config.Options;
import org.linqs.psl.config.RuntimeOptions;
import org.linqs.psl.database.DataStore;
import org.linqs.psl.database.Database;
import org.linqs.psl.database.Partition;
import org.linqs.psl.database.loading.Inserter;
import org.linqs.psl.database.rdbms.RDBMSDataStore;
import org.linqs.psl.database.rdbms.driver.DatabaseDriver;
import org.linqs.psl.database.rdbms.driver.H2DatabaseDriver;
import org.linqs.psl.database.rdbms.driver.PostgreSQLDriver;
import org.linqs.psl.database.rdbms.driver.SQLiteDriver;
import org.linqs.psl.evaluation.EvaluationInstance;
import org.linqs.psl.evaluation.statistics.Evaluator;
import org.linqs.psl.grounding.Grounding;
import org.linqs.psl.model.Model;
import org.linqs.psl.model.atom.GroundAtom;
import org.linqs.psl.model.atom.RandomVariableAtom;
import org.linqs.psl.model.predicate.DeepPredicate;
import org.linqs.psl.model.predicate.Predicate;
import org.linqs.psl.model.predicate.StandardPredicate;
import org.linqs.psl.model.rule.GroundRule;
import org.linqs.psl.model.rule.Rule;
import org.linqs.psl.model.rule.WeightedGroundRule;
import org.linqs.psl.util.FileUtils;
import org.linqs.psl.util.Logger;
import org.linqs.psl.util.Parallel;
import org.linqs.psl.util.Reflection;
import org.linqs.psl.util.StringUtils;
import org.linqs.psl.util.Version;

import java.io.BufferedWriter;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * Launches PSL from the command line.
 * Supports inference and supervised parameter learning.
 */
public class Runtime {
    private static final Logger log = Logger.getLogger(Runtime.class);

    public static final String PARTITION_NAME_OBSERVATIONS = "observations";
    public static final String PARTITION_NAME_TARGET = "targets";
    public static final String PARTITION_NAME_TRUTH = "truth";

    private static final String[] PARTITION_NAMES = new String[]{
        PARTITION_NAME_OBSERVATIONS,
        PARTITION_NAME_TARGET,
        PARTITION_NAME_TRUTH
    };

    public Runtime() {
        initLogger();
    }

    public RuntimeResult run() {
        return run(new RuntimeConfig());
    }

    public RuntimeResult run(String configPath) {
        return run(configPath, false);
    }

    public RuntimeResult run(String configPath, boolean fillResult) {
        return run(RuntimeConfig.fromFile(configPath), fillResult);
    }

    public RuntimeResult run(RuntimeConfig config) {
        return run(config, false);
    }

    /**
     * A static interface specifically meant for methods that provide serialized input and want serialized output
     * (both in the form of JSON).
     */
    public static String serializedRun(String jsonConfig, String basePath) {
        Runtime runtime = new Runtime();
        RuntimeResult result = runtime.run(RuntimeConfig.fromJSON(jsonConfig, basePath), true);
        runtime.cleanup();

        return result.toJSON();
    }

    /**
     * The primary interface into a PSL runtime.
     * Options specified in the config will be applied during the runtime, and reset after.
     */
    public RuntimeResult run(RuntimeConfig config, boolean fillResult) {
        Config.pushLayer();

        try {
            return runInternal(config, fillResult);
        } finally {
            Config.popLayer();
            cleanup();
        }
    }

    protected RuntimeResult runInternal(RuntimeConfig config, boolean fillResult) {
        RuntimeResult result = null;
        if (fillResult) {
            result = new RuntimeResult();
        }

        // Apply any top-level options found in the config.
        for (Map.Entry entry : config.options.entrySet()) {
            Config.setProperty(entry.getKey(), entry.getValue(), false);
        }

        // Specially check if we need to re-init the logger.
        initLogger();

        if (checkHelp() || checkVersion()) {
            return result;
        }

        log.info("PSL Runtime Version {}", Version.getFull());
        config.validate();

        // Apply top-level options again after validation (since options may have been changed or added).
        for (Map.Entry entry : config.options.entrySet()) {
            Config.setProperty(entry.getKey(), entry.getValue(), false);
        }

        // Set the relative base path for all other paths.
        Config.setProperty("runtime.relativebasepath", config.relativeBasePath, false);

        // Set all predicate options inside each predicate.
        for (RuntimeConfig.PredicateConfigInfo info : config.predicates.values()) {
            Predicate predicate = Predicate.get(info.name);
            for (Map.Entry entry : info.options.entrySet()) {
                predicate.setPredicateOption(entry.getKey(), entry.getValue());
            }
        }

        Model model = null;
        if (RuntimeOptions.LEARN.getBoolean()) {
            model = runLearning(config, result);
        }

        if (RuntimeOptions.INFERENCE.getBoolean()) {
            runInference(config, model, result);
        }

        // TODO(Connor): Closing DeepPredicates needs to occur after both learning and inference.
        for (Predicate predicate : Predicate.getAll()) {
            if (predicate instanceof DeepPredicate) {
                predicate.close();
            }
        }

        return result;
    }

    protected boolean checkHelp() {
        if (!RuntimeOptions.HELP.getBoolean()) {
            return false;
        }

        System.out.println("PSL Runtime Version " + Version.getFull());
        System.out.println("Options used by the PSL runtime:");

        List




© 2015 - 2025 Weber Informatics LLC | Privacy Policy