#!/usr/bin/env python3 from util import randomSAT from util import kSAT import util.script as scriptUtils import pymongo import ssl def main(): args = __parseArguments() dbContext = __getDBContext(args["dbConfigPath"]) __generateExperiment(args, dbContext) dbContext["client"].close() def __generateExperiment(args, dbContext): experimentScope = __prepareExperimentScope(args) for i in range(args["instances"]): sat = randomSAT.generateRandomKSAT(args["clauses"], args["variables"], args["variablesPerClause"]) instanceId = dbContext["instances"].insert_one(__packDocument(sat)).inserted_id experimentScope["instances"].append(instanceId) dbContext["experimentScopes"].insert_one(experimentScope) def __packDocument(instance): doc = instance.writeJSONLike(); doc["degrees_of_variables"] = __packDegreesOfVariables(instance) doc["conflicts"] = __packConflicts(instance) return doc def __packDegreesOfVariables(instance): doc = [] for var, degree in instance.getDegreesOfVariables().items(): doc.append({"var": var, "deg": degree}) return doc def __packConflicts(instance): doc = [{"var": i + 1, "clauses": { "pos_lit": [], "neg_lit": []}} for i in range(instance.getNumberOfVariables())] for conflict in instance.getConflicts(): for binding in conflict: clause = binding[0] lit = binding[1] varIndex = abs(lit) - 1 if lit > 0: if clause not in doc[varIndex]["clauses"]["pos_lit"]: doc[varIndex]["clauses"]["pos_lit"].append(clause) else: if clause not in doc[varIndex]["clauses"]["neg_lit"]: doc[varIndex]["clauses"]["neg_lit"].append(clause) return doc def __prepareExperimentScope(args): experimentScope = {} experimentScope["instances"] = [] description = "This experiment contains %d instances " % args["instances"] description += "each with %d clauses, %d variables " % (args["clauses"], args["variables"]) description += ("and %d variables per clause (c/v = %.2f)" %(args["variablesPerClause"], float(args["clauses"]) / float(args["variables"]))) experimentScope["description"] = description experimentScope["_id"] = args["experimentId"].strip() return experimentScope def __getDBClient(dbConfigPath): dbConf = scriptUtils.readConfig(dbConfigPath) dbConf["CONNECTION"] return pymongo.MongoClient( "mongodb://%s:%s@%s:%s/%s" % ( dbConf["CONNECTION"]["user"], dbConf["CONNECTION"]["pw"], dbConf["CONNECTION"]["url"], dbConf["CONNECTION"]["port"], dbConf["CONNECTION"]["database"]), ssl=True, ssl_cert_reqs=ssl.CERT_NONE) def __getDBContext(dbConfigPath): dbContext = {} dbContext["client"] = __getDBClient(dbConfigPath) dbContext["db"] = dbContext["client"]["experiments"] dbContext["instances"] = dbContext["db"]["instances"] dbContext["experimentScopes"] = dbContext["db"]["experiment_scopes"] return dbContext def __parseArguments(): parser = scriptUtils.ArgParser() parser.addArg(alias="instances", shortFlag="i", longFlag="instances", help="number of random kSAT instances", type=int) parser.addArg(alias="variables", shortFlag="v", longFlag="variables", help="number of variables in the ksat instances", type=int) parser.addArg(alias="clauses", shortFlag="c", longFlag="clauses", help="number of clauses in the ksat instances", type=int) parser.addArg(alias="variablesPerClause", shortFlag="vpc", longFlag="variables_per_clause", help="variables per clause in the kSAT instances", type=int, default=3) parser.addArg(alias="dbConfigPath", shortFlag="d", longFlag="db_config", help="path to the database config file", type=str, default="database.config") parser.addArg(alias="experimentId", shortFlag="id", longFlag="experiment_id", help="the name or id of the experiment", type=str) return parser.parse() if __name__ == "__main__": main()