コード例 #1
0
  public ASTNode substituteCommonTerms(ASTNode tree, IExpressionContext context) {

    ASTNode copy = tree.createCopy(true);

    final Map<Integer, List<ASTNode>> result = new HashMap<>();

    final INodeVisitor visitor =
        new INodeVisitor() {

          @Override
          public boolean visit(ASTNode node, int currentDepth) {
            final Integer hash = node.hashCode();
            List<ASTNode> existing = result.get(hash);
            if (existing == null) {
              existing = new ArrayList<>();
              result.put(hash, existing);
            }
            existing.add(node);
            return true;
          }
        };
    tree.visitInOrder(visitor);

    outer:
    for (Map.Entry<Integer, List<ASTNode>> entry : result.entrySet()) {
      final int hash = entry.getKey();

      if (entry.getValue().size() <= 1) {
        continue;
      }

      for (ASTNode n : entry.getValue()) {
        if (n instanceof IdentifierNode) {
          continue outer;
        }
      }

      // create new variable
      final ASTNode value = entry.getValue().get(0).createCopy(true);
      final Identifier identifier = context.createIdentifier(value);

      final boolean substituted = replaceMatchingTermsWithVariable(context, copy, hash, identifier);

      if (substituted) {
        debugPrintln(
            "SUBSTITUTE: "
                + value
                + " => "
                + identifier
                + " ( "
                + entry.getValue().size()
                + " times )");
      } else {
        context.remove(identifier);
      }
    }
    return copy;
  }
コード例 #2
0
  public ASTNode expand(ASTNode term, IExpressionContext context, boolean deleteExpandedVars) {
    final ASTNode result = term.createCopy(true);

    final Set<Identifier> expandedIdentifiers = new HashSet<>();

    boolean expanded = false;
    do {
      expanded = false;
      final MutatingNodeVisitor visitor =
          new MutatingNodeVisitor(context) {

            @Override
            public void visit(ASTNode node, IExpressionContext context, IIterationContext it) {
              final ASTNode unwrapped = unwrap(node);
              if (node.hasParent() && unwrapped instanceof IdentifierNode) {
                final ASTNode expanded = unwrapped.evaluate(context);
                if (expanded != null && expanded != unwrapped) {
                  debugPrintln("EXPAND: Expanding " + node + " -> " + expanded);
                  expandedIdentifiers.add(((IdentifierNode) unwrapped).getIdentifier());
                  node.replaceWith(expanded);
                  it.astMutated();
                }
              }
            }
          };

      expanded = applyPostOrder(result, visitor);
    } while (expanded);

    if (deleteExpandedVars) {
      for (Identifier id : expandedIdentifiers) {
        context.remove(id);
      }
    }

    return result;
  }