37     Program& program = translationUnit.getProgram();
 
   38     auto* ioTypes = translationUnit.getAnalysis<analysis::IOTypeAnalysis>();
 
   39     std::set<QualifiedName> emptyRelations;
 
   41     for (
auto rel : program.getRelations()) {
 
   45         emptyRelations.insert(
rel->getQualifiedName());
 
   47         bool usedInAggregate = 
false;
 
   50                 visitDepthFirst(*lit, [&](const Atom& atom) {
 
   51                     if (getAtomRelation(&atom, &program) == rel) {
 
   52                         usedInAggregate = true;
 
   58         if (!usedInAggregate && !ioTypes->isOutput(
rel)) {
 
   64     for (
const auto& relName : emptyRelations) {
 
   65         changed |= removeEmptyRelationUses(translationUnit, relName);
 
   71 bool RemoveEmptyRelationsTransformer::removeEmptyRelationUses(
 
   72         TranslationUnit& translationUnit, 
const QualifiedName& emptyRelationName) {
 
   73     Program& program = translationUnit.getProgram();
 
   81     std::vector<const Clause*> 
clauses;
 
   89         for (
Literal* lit : cl->getBodyLiterals()) {
 
   90             if (
auto* arg = 
dynamic_cast<Atom*
>(lit)) {
 
   91                 if (arg->getQualifiedName() == emptyRelationName) {
 
   92                     program.removeClause(cl);
 
  103             bool rewrite = 
false;
 
  104             for (Literal* lit : cl->getBodyLiterals()) {
 
  105                 if (
auto* neg = 
dynamic_cast<Negation*
>(lit)) {
 
  106                     if (neg->getAtom()->getQualifiedName() == emptyRelationName) {
 
  118                 for (Literal* lit : cl->getBodyLiterals()) {
 
  119                     if (
auto* neg = 
dynamic_cast<Negation*
>(lit)) {
 
  120                         if (neg->getAtom()->getQualifiedName() != emptyRelationName) {
 
  128                 program.removeClause(cl);
 
  129                 program.addClause(std::move(res));