Branch data Line data Source code
1 : : /****************************************************************************** 2 : : * This file is part of the cvc5 project. 3 : : * 4 : : * Copyright (c) 2009-2026 by the authors listed in the file AUTHORS 5 : : * in the top-level source directory and their institutional affiliations. 6 : : * All rights reserved. See the file COPYING in the top-level source 7 : : * directory for licensing information. 8 : : * **************************************************************************** 9 : : * 10 : : * Node converter utility 11 : : */ 12 : : 13 : : #include "cvc5_private.h" 14 : : 15 : : #ifndef CVC5__EXPR__NODE_CONVERTER_H 16 : : #define CVC5__EXPR__NODE_CONVERTER_H 17 : : 18 : : #include <iostream> 19 : : #include <map> 20 : : 21 : : #include "expr/node.h" 22 : : #include "expr/type_node.h" 23 : : 24 : : namespace cvc5::internal { 25 : : 26 : : /** 27 : : * A node converter for terms and types. Implements term/type traversals, 28 : : * calling the provided implementations of conversion methods (pre/postConvert 29 : : * and pre/postConvertType) at pre-traversal and post-traversal. 30 : : * 31 : : * This class can be used as a generic method for converting terms/types, which 32 : : * is orthogonal to methods for traversing nodes. 33 : : */ 34 : : class NodeConverter 35 : : { 36 : : public: 37 : : /** 38 : : * @param forceIdem If true, this assumes that terms returned by postConvert 39 : : * and postConvertType should not be converted again. 40 : : */ 41 : : NodeConverter(NodeManager* nm, bool forceIdem = true); 42 : 763086 : virtual ~NodeConverter() {} 43 : : /** 44 : : * This converts node n based on the preConvert/postConvert methods that can 45 : : * be overriden by instances of this class. 46 : : * 47 : : * If n is null, this always returns the null node. 48 : : * 49 : : * @param preserveTypes If true, we make calls to postConvert below for the 50 : : * conversion, which requires that the conversion preserves the types of 51 : : * all subterms in n. If false, we make calls to postConvertUntyped, which 52 : : * may change the type of subterms. 53 : : */ 54 : : Node convert(Node n, bool preserveTypes = true); 55 : : 56 : : /** 57 : : * This converts type node n based on the preConvertType/postConvertType 58 : : * methods that can be overriden by instances of this class. 59 : : */ 60 : : TypeNode convertType(TypeNode tn); 61 : : 62 : : protected: 63 : : //------------------------- virtual interface 64 : : /** Should we traverse n? */ 65 : : virtual bool shouldTraverse(Node n); 66 : : /** 67 : : * Run the conversion for n during pre-order traversal. 68 : : * Returning null is equivalent to saying the node should not be changed. 69 : : * 70 : : * If convert is called with preserveTypes=true, then we require that the 71 : : * type of the returned term (if non-null) is the same as the type of n. 72 : : */ 73 : : virtual Node preConvert(Node n); 74 : : /** 75 : : * Run the conversion for post-order traversal, where notice n is a term 76 : : * of the form: 77 : : * (f i_1 ... i_m) 78 : : * where i_1, ..., i_m are terms that have been returned by previous calls 79 : : * to postConvert. 80 : : * 81 : : * Returning null is equivalent to saying the node should not be changed. 82 : : * 83 : : * We require that the type of the returned term (if non-null) is the same 84 : : * as the type of n. 85 : : */ 86 : : virtual Node postConvert(Node n); 87 : : /** 88 : : * Run the conversion for post-porder traversal. If orig is of the form 89 : : * (f e_1 ... e_m), then terms is {i_1, ..., i_m}, where i_1, ..., i_m 90 : : * is the result of converting e_1, ..., e_m. In contrast to the above 91 : : * method, the type of the returned term does not need to match the type 92 : : * of orig. The method also takes whether any of the elements of terms differ 93 : : * from the children of orig. 94 : : */ 95 : : virtual Node postConvertUntyped(Node orig, 96 : : const std::vector<Node>& terms, 97 : : bool termsChanged); 98 : : /** 99 : : * Run the conversion, same as `preConvert`, but for type nodes, which notice 100 : : * can be built from children similar to Node. 101 : : */ 102 : : virtual TypeNode preConvertType(TypeNode n); 103 : : /** 104 : : * Run the conversion, same as `postConvert`, but for type nodes, which notice 105 : : * can be built from children similar to Node. 106 : : */ 107 : : virtual TypeNode postConvertType(TypeNode n); 108 : : //------------------------- end virtual interface 109 : : protected: 110 : : /** The underlying node manager */ 111 : : NodeManager* d_nm; 112 : : 113 : : private: 114 : : /** Add to cache */ 115 : : void addToCache(TNode cur, TNode ret); 116 : : /** Add to type cache */ 117 : : void addToTypeCache(TypeNode cur, TypeNode ret); 118 : : /** Node cache for preConvert */ 119 : : std::unordered_map<Node, Node> d_preCache; 120 : : /** Node cache for postConvert */ 121 : : std::unordered_map<Node, Node> d_cache; 122 : : /** TypeNode cache for preConvert */ 123 : : std::unordered_map<TypeNode, TypeNode> d_preTCache; 124 : : /** TypeNode cache for postConvert */ 125 : : std::unordered_map<TypeNode, TypeNode> d_tcache; 126 : : /** Whether this node converter is idempotent. */ 127 : : bool d_forceIdem; 128 : : }; 129 : : 130 : : } // namespace cvc5::internal 131 : : 132 : : #endif