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 : : * Utilities for computing letification of proofs.
11 : : */
12 : :
13 : : #include "proof/proof_letify.h"
14 : :
15 : : namespace cvc5::internal {
16 : : namespace proof {
17 : :
18 : 0 : bool ProofLetifyTraverseCallback::shouldTraverse(const ProofNode* pn)
19 : : {
20 : 0 : return pn->getRule() != ProofRule::SCOPE;
21 : : }
22 : :
23 : 425139 : void ProofLetify::computeProofLet(const ProofNode* pn,
24 : : std::vector<const ProofNode*>& pletList,
25 : : std::map<const ProofNode*, size_t>& pletMap,
26 : : size_t thresh,
27 : : ProofLetifyTraverseCallback* pltc)
28 : : {
29 [ + - ][ + - ]: 425139 : Assert(pletList.empty() && pletMap.empty());
[ - + ][ - + ]
[ - - ]
30 [ - + ]: 425139 : if (thresh == 0)
31 : : {
32 : : // value of 0 means do not introduce let
33 : 0 : return;
34 : : }
35 : 425139 : std::vector<const ProofNode*> visitList;
36 : 425139 : std::map<const ProofNode*, size_t> pcount;
37 [ - + ]: 425139 : if (pltc == nullptr)
38 : : {
39 : : // use default callback
40 : 0 : ProofLetifyTraverseCallback defaultPltc;
41 : 0 : computeProofCounts(pn, visitList, pcount, &defaultPltc);
42 : 0 : }
43 : : else
44 : : {
45 : 425139 : computeProofCounts(pn, visitList, pcount, pltc);
46 : : }
47 : : // Now populate the pletList and pletMap
48 : 425139 : convertProofCountToLet(visitList, pcount, pletList, pletMap, thresh);
49 : 425139 : }
50 : :
51 : 425139 : void ProofLetify::computeProofCounts(const ProofNode* pn,
52 : : std::vector<const ProofNode*>& visitList,
53 : : std::map<const ProofNode*, size_t>& pcount,
54 : : ProofLetifyTraverseCallback* pltc)
55 : : {
56 : 425139 : std::map<const ProofNode*, size_t>::iterator it;
57 : 425139 : std::vector<const ProofNode*> visit;
58 : : const ProofNode* cur;
59 : 425139 : visit.push_back(pn);
60 : : do
61 : : {
62 : 36099815 : cur = visit.back();
63 : 36099815 : it = pcount.find(cur);
64 [ + + ]: 36099815 : if (it == pcount.end())
65 : : {
66 : 16322804 : pcount[cur] = 0;
67 [ + + ]: 16322804 : if (!pltc->shouldTraverse(cur))
68 : : {
69 : : // callback indicated we should not traverse
70 : 401269 : continue;
71 : : }
72 : 15921535 : const std::vector<std::shared_ptr<ProofNode>>& pc = cur->getChildren();
73 [ + + ]: 35273407 : for (const std::shared_ptr<ProofNode>& cp : pc)
74 : : {
75 : 19351872 : visit.push_back(cp.get());
76 : : }
77 : : }
78 : : else
79 : : {
80 [ + + ]: 19777011 : if (it->second == 0)
81 : : {
82 : 16322804 : visitList.push_back(cur);
83 : : }
84 : 19777011 : pcount[cur]++;
85 : 19777011 : visit.pop_back();
86 : : }
87 [ + + ]: 36099815 : } while (!visit.empty());
88 : 425139 : }
89 : :
90 : 425139 : void ProofLetify::convertProofCountToLet(
91 : : const std::vector<const ProofNode*>& visitList,
92 : : const std::map<const ProofNode*, size_t>& pcount,
93 : : std::vector<const ProofNode*>& pletList,
94 : : std::map<const ProofNode*, size_t>& pletMap,
95 : : size_t thresh)
96 : : {
97 [ + - ][ + - ]: 425139 : Assert(pletList.empty() && pletMap.empty());
[ - + ][ - + ]
[ - - ]
98 [ - + ]: 425139 : if (thresh == 0)
99 : : {
100 : : // value of 0 means do not introduce let
101 : 0 : return;
102 : : }
103 : : // Assign ids for those whose count is > 1, traverse in reverse order
104 : : // so that deeper proofs are assigned lower identifiers
105 : 425139 : std::map<const ProofNode*, size_t>::const_iterator itc;
106 [ + + ]: 16747943 : for (const ProofNode* pn : visitList)
107 : : {
108 : 16322804 : itc = pcount.find(pn);
109 [ - + ][ - + ]: 16322804 : Assert(itc != pcount.end());
[ - - ]
110 [ + + ][ + + ]: 16322804 : if (itc->second >= thresh && pn->getRule() != ProofRule::ASSUME)
[ + + ]
111 : : {
112 : 1442996 : pletList.push_back(pn);
113 : : // start with id 1
114 : 1442996 : size_t id = pletMap.size() + 1;
115 : 1442996 : pletMap[pn] = id;
116 : : }
117 : : }
118 : : }
119 : :
120 : : } // namespace proof
121 : : } // namespace cvc5::internal
|