public static DefaultRule representativeSubstitution( DefaultRule rule, List<Set<Constant>> interchangeable) { if (rule.antecedent().variables().isEmpty()) { return rule; } else { // a bit naive (but not too much), it can be improved later... List<Literal> auxLiteralsC = new ArrayList<Literal>(); for (Variable v : rule.antecedent().variables()) { auxLiteralsC.add(new Literal("v", v)); } List<Literal> auxLiteralsE = new ArrayList<Literal>(); int typeIndex = 0; for (Set<Constant> interch : interchangeable) { int counter = 0; for (Term t : interch) { auxLiteralsE.add(new Literal("v", t)); if (++counter >= rule.antecedent().variables().size()) { break; } } } Matching m = new Matching(); m.setSubsumptionMode(Matching.OI_SUBSUMPTION); Pair<Term[], List<Term[]>> substitutions = m.allSubstitutions(new Clause(auxLiteralsC), new Clause(auxLiteralsE), 1); return DefaultTransformationUtils.substitute(rule, substitutions.r, substitutions.s.get(0)); } }