selectorType,
"is an unresolved selector type placeholder",
NodeManager::SKOLEM_EXACT_NAME | NodeManager::SKOLEM_NO_NOTIFY);
- Trace("datatypes") << type << std::endl;
+ Trace("datatypes") << "DTypeConstructor::addArg: " << type << std::endl;
std::shared_ptr<DTypeSelector> a =
std::make_shared<DTypeSelector>(selectorName, type);
addArg(a);
d_args.push_back(a);
}
+void DTypeConstructor::addArgSelf(std::string selectorName)
+{
+ Trace("datatypes") << "DTypeConstructor::addArgSelf" << std::endl;
+ std::shared_ptr<DTypeSelector> a =
+ std::make_shared<DTypeSelector>(selectorName, Node::null());
+ addArg(a);
+}
+
std::string DTypeConstructor::getName() const { return d_name; }
Node DTypeConstructor::getConstructor() const
return -1;
}
+int DTypeConstructor::getSelectorIndexForName(const std::string& name) const
+{
+ for (size_t i = 0, nargs = getNumArgs(); i < nargs; i++)
+ {
+ if (d_args[i]->getName() == name)
+ {
+ return i;
+ }
+ }
+ return -1;
+}
+
bool DTypeConstructor::involvesExternalType() const
{
for (size_t i = 0, nargs = getNumArgs(); i < nargs; i++)
namespace CVC4 {
-class DatatypeConstructor;
-
/**
* The Node-level representation of a constructor for a datatype, which
* currently resides in the Expr-level DatatypeConstructor class
*/
class DTypeConstructor
{
- friend class DatatypeConstructor;
friend class DType;
public:
* Add an argument, given a pointer to a selector object.
*/
void addArg(std::shared_ptr<DTypeSelector> a);
+ /**
+ * Add a self-referential (i.e., a data field) of the given name
+ * to this Datatype constructor that refers to the enclosing
+ * Datatype. For example, using the familiar "nat" Datatype, to
+ * create the "pred" field for "succ" constructor, one uses
+ * succ::addArgSelf("pred")---the actual Type
+ * cannot be passed because the Datatype is still under
+ * construction. Selector names need not be unique; they are for
+ * convenience and pretty-printing only.
+ *
+ * This is a special case of
+ * DTypeConstructor::addArg(std::string).
+ */
+ void addArgSelf(std::string selectorName);
/** Get the name of this constructor. */
std::string getName() const;
* stoa(T,C,index)
*/
int getSelectorIndexInternal(Node sel) const;
+ /** get selector index for name
+ *
+ * Returns the index of selector with the given name, or -1 if it
+ * does not exist.
+ */
+ int getSelectorIndexForName(const std::string& name) const;
/** involves external type
*
throw TypeCheckingExceptionPrivate(
n, "Record-update expression formed over non-record");
}
- const Record& rec =
- DatatypeType(recordType.toType()).getRecord();
- if (!rec.contains(ru.getField())) {
+ const DType& dt = recordType.getDType();
+ const DTypeConstructor& recCons = dt[0];
+ if (recCons.getSelectorIndexForName(ru.getField()) == -1)
+ {
std::stringstream ss;
ss << "Record-update field `" << ru.getField()
<< "' is not a valid field name for the record type";