diff --git a/eidos/eidos_interpreter.cpp b/eidos/eidos_interpreter.cpp index db79226f..c6aeb1c3 100644 --- a/eidos/eidos_interpreter.cpp +++ b/eidos/eidos_interpreter.cpp @@ -3771,89 +3771,48 @@ EidosValue_SP EidosInterpreter::Evaluate_Assign(const EidosASTNode *p_node) { EidosTokenType compound_operator = rvalue_node->token_->token_type_; int64_t operand2_value = cached_operand2->IntAtIndex_NOCAST(0, nullptr); + int64_t *int_data = lvalue->IntData_Mutable(); - if ((lvalue_count == 1) && lvalue->IsSingleton()) + switch (compound_operator) { - EidosValue_Int *int_singleton = static_cast(lvalue); - - switch (compound_operator) + case EidosTokenType::kTokenPlus: { - case EidosTokenType::kTokenPlus: + for (int value_index = 0; value_index < lvalue_count; ++value_index) { - int64_t &operand1_value = int_singleton->IntData_Mutable()[0]; - bool overflow = Eidos_add_overflow(operand1_value, operand2_value, &operand1_value); + int64_t &int_vec_value = int_data[value_index]; + bool overflow = Eidos_add_overflow(int_vec_value, operand2_value, &int_vec_value); if (overflow) EIDOS_TERMINATION << "ERROR (EidosInterpreter::Evaluate_Assign): integer addition overflow with the binary '+' operator." << EidosTerminate(rvalue_node->token_); - goto compoundAssignmentSuccess; } - case EidosTokenType::kTokenMinus: + goto compoundAssignmentSuccess; + } + case EidosTokenType::kTokenMinus: + { + for (int value_index = 0; value_index < lvalue_count; ++value_index) { - int64_t &operand1_value = int_singleton->IntData_Mutable()[0]; - bool overflow = Eidos_sub_overflow(operand1_value, operand2_value, &operand1_value); + int64_t &int_vec_value = int_data[value_index]; + bool overflow = Eidos_sub_overflow(int_vec_value, operand2_value, &int_vec_value); if (overflow) EIDOS_TERMINATION << "ERROR (EidosInterpreter::Evaluate_Assign): integer subtraction overflow with the binary '-' operator." << EidosTerminate(rvalue_node->token_); - goto compoundAssignmentSuccess; } - case EidosTokenType::kTokenMult: + goto compoundAssignmentSuccess; + } + case EidosTokenType::kTokenMult: + { + for (int value_index = 0; value_index < lvalue_count; ++value_index) { - int64_t &operand1_value = int_singleton->IntData_Mutable()[0]; - bool overflow = Eidos_mul_overflow(operand1_value, operand2_value, &operand1_value); + int64_t &int_vec_value = int_data[value_index]; + bool overflow = Eidos_mul_overflow(int_vec_value, operand2_value, &int_vec_value); if (overflow) EIDOS_TERMINATION << "ERROR (EidosInterpreter::Evaluate_Assign): integer multiplication overflow with the '*' operator." << EidosTerminate(rvalue_node->token_); - goto compoundAssignmentSuccess; - } - default: // div, mod, and exp always produce float, so we don't handle them for int; we can't change the type of x here - break; - } - } - else - { - int64_t *int_data = lvalue->IntData_Mutable(); - - switch (compound_operator) - { - case EidosTokenType::kTokenPlus: - { - for (int value_index = 0; value_index < lvalue_count; ++value_index) - { - int64_t &int_vec_value = int_data[value_index]; - bool overflow = Eidos_add_overflow(int_vec_value, operand2_value, &int_vec_value); - - if (overflow) - EIDOS_TERMINATION << "ERROR (EidosInterpreter::Evaluate_Assign): integer addition overflow with the binary '+' operator." << EidosTerminate(rvalue_node->token_); - } - goto compoundAssignmentSuccess; } - case EidosTokenType::kTokenMinus: - { - for (int value_index = 0; value_index < lvalue_count; ++value_index) - { - int64_t &int_vec_value = int_data[value_index]; - bool overflow = Eidos_sub_overflow(int_vec_value, operand2_value, &int_vec_value); - - if (overflow) - EIDOS_TERMINATION << "ERROR (EidosInterpreter::Evaluate_Assign): integer subtraction overflow with the binary '-' operator." << EidosTerminate(rvalue_node->token_); - } - goto compoundAssignmentSuccess; - } - case EidosTokenType::kTokenMult: - { - for (int value_index = 0; value_index < lvalue_count; ++value_index) - { - int64_t &int_vec_value = int_data[value_index]; - bool overflow = Eidos_mul_overflow(int_vec_value, operand2_value, &int_vec_value); - - if (overflow) - EIDOS_TERMINATION << "ERROR (EidosInterpreter::Evaluate_Assign): integer multiplication overflow with the '*' operator." << EidosTerminate(rvalue_node->token_); - } - goto compoundAssignmentSuccess; - } - default: // div, mod, and exp always produce float, so we don't handle them for int; we can't change the type of x here - break; + goto compoundAssignmentSuccess; } + default: // div, mod, and exp always produce float, so we don't handle them for int; we can't change the type of x here + break; } } } @@ -3864,99 +3823,51 @@ EidosValue_SP EidosInterpreter::Evaluate_Assign(const EidosASTNode *p_node) EidosValue *cached_operand2 = rvalue_node->children_[1]->cached_literal_value_.get(); // the numeric constant EidosTokenType compound_operator = rvalue_node->token_->token_type_; double operand2_value = cached_operand2->NumericAtIndex_NOCAST(0, nullptr); // might be an int64_t and get converted + double *float_data = lvalue->FloatData_Mutable(); - if ((lvalue_count == 1) && lvalue->IsSingleton()) + switch (compound_operator) { - EidosValue_Float *float_singleton = static_cast(lvalue); - - switch (compound_operator) - { - case EidosTokenType::kTokenPlus: - float_singleton->FloatData_Mutable()[0] += operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenMinus: - float_singleton->FloatData_Mutable()[0] -= operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenMult: - float_singleton->FloatData_Mutable()[0] *= operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenDiv: - float_singleton->FloatData_Mutable()[0] /= operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenMod: + case EidosTokenType::kTokenPlus: + for (int value_index = 0; value_index < lvalue_count; ++value_index) + float_data[value_index] += operand2_value; + goto compoundAssignmentSuccess; + + case EidosTokenType::kTokenMinus: + for (int value_index = 0; value_index < lvalue_count; ++value_index) + float_data[value_index] -= operand2_value; + goto compoundAssignmentSuccess; + + case EidosTokenType::kTokenMult: + for (int value_index = 0; value_index < lvalue_count; ++value_index) + float_data[value_index] *= operand2_value; + goto compoundAssignmentSuccess; + + case EidosTokenType::kTokenDiv: + for (int value_index = 0; value_index < lvalue_count; ++value_index) + float_data[value_index] /= operand2_value; + goto compoundAssignmentSuccess; + + case EidosTokenType::kTokenMod: + for (int value_index = 0; value_index < lvalue_count; ++value_index) { - double &operand1_value = float_singleton->FloatData_Mutable()[0]; + double &float_vec_value = float_data[value_index]; - operand1_value = fmod(operand1_value, operand2_value); - goto compoundAssignmentSuccess; + float_vec_value = fmod(float_vec_value, operand2_value); } - - case EidosTokenType::kTokenExp: + goto compoundAssignmentSuccess; + + case EidosTokenType::kTokenExp: + for (int value_index = 0; value_index < lvalue_count; ++value_index) { - double &operand1_value = float_singleton->FloatData_Mutable()[0]; + double &float_vec_value = float_data[value_index]; - operand1_value = pow(operand1_value, operand2_value); - goto compoundAssignmentSuccess; + float_vec_value = pow(float_vec_value, operand2_value); } - - default: - // CODE COVERAGE: This is dead code - break; - } - - } - else - { - double *float_data = lvalue->FloatData_Mutable(); - - switch (compound_operator) - { - case EidosTokenType::kTokenPlus: - for (int value_index = 0; value_index < lvalue_count; ++value_index) - float_data[value_index] += operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenMinus: - for (int value_index = 0; value_index < lvalue_count; ++value_index) - float_data[value_index] -= operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenMult: - for (int value_index = 0; value_index < lvalue_count; ++value_index) - float_data[value_index] *= operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenDiv: - for (int value_index = 0; value_index < lvalue_count; ++value_index) - float_data[value_index] /= operand2_value; - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenMod: - for (int value_index = 0; value_index < lvalue_count; ++value_index) - { - double &float_vec_value = float_data[value_index]; - - float_vec_value = fmod(float_vec_value, operand2_value); - } - goto compoundAssignmentSuccess; - - case EidosTokenType::kTokenExp: - for (int value_index = 0; value_index < lvalue_count; ++value_index) - { - double &float_vec_value = float_data[value_index]; - - float_vec_value = pow(float_vec_value, operand2_value); - } - goto compoundAssignmentSuccess; - - default: - // CODE COVERAGE: This is dead code - break; - } + goto compoundAssignmentSuccess; + + default: + // CODE COVERAGE: This is dead code + break; } goto compoundAssignmentSuccess; diff --git a/eidos/eidos_value.cpp b/eidos/eidos_value.cpp index d2021808..413a9ceb 100644 --- a/eidos/eidos_value.cpp +++ b/eidos/eidos_value.cpp @@ -321,7 +321,7 @@ int EidosValue::valueTrackingCount; std::vector EidosValue::valueTrackingVector; #endif -EidosValue::EidosValue(EidosValueType p_value_type, bool p_singleton) : intrusive_ref_count_(0), cached_type_(p_value_type), constant_(false), invisible_(false), is_singleton_(p_singleton), dim_(nullptr) +EidosValue::EidosValue(EidosValueType p_value_type) : intrusive_ref_count_(0), cached_type_(p_value_type), constant_(false), invisible_(false), dim_(nullptr) { #ifdef EIDOS_TRACK_VALUE_ALLOCATION valueTrackingCount++; @@ -968,7 +968,7 @@ void EidosValue_NULL::Sort(bool p_ascending) #pragma mark EidosValue_Logical #pragma mark - -EidosValue_Logical::EidosValue_Logical(const std::vector &p_logicalvec) : EidosValue(EidosValueType::kValueLogical, false) +EidosValue_Logical::EidosValue_Logical(const std::vector &p_logicalvec) : EidosValue(EidosValueType::kValueLogical) { size_t count = p_logicalvec.size(); const eidos_logical_t *values = p_logicalvec.data(); @@ -979,12 +979,12 @@ EidosValue_Logical::EidosValue_Logical(const std::vector &p_log set_logical_no_check(values[index], index); } -EidosValue_Logical::EidosValue_Logical(eidos_logical_t p_logical1) : EidosValue(EidosValueType::kValueLogical, false) // protected +EidosValue_Logical::EidosValue_Logical(eidos_logical_t p_logical1) : EidosValue(EidosValueType::kValueLogical) // protected { push_logical(p_logical1); } -EidosValue_Logical::EidosValue_Logical(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueLogical, false) +EidosValue_Logical::EidosValue_Logical(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueLogical) { reserve(p_init_list.size()); @@ -992,7 +992,7 @@ EidosValue_Logical::EidosValue_Logical(std::initializer_list p_ push_logical_no_check(init_item); } -EidosValue_Logical::EidosValue_Logical(const eidos_logical_t *p_values, size_t p_count) : EidosValue(EidosValueType::kValueLogical, false) +EidosValue_Logical::EidosValue_Logical(const eidos_logical_t *p_values, size_t p_count) : EidosValue(EidosValueType::kValueLogical) { resize_no_initialize(p_count); @@ -1168,17 +1168,17 @@ void EidosValue_Logical::erase_index(size_t p_index) #pragma mark EidosValue_String #pragma mark - -EidosValue_String::EidosValue_String(const std::vector &p_stringvec) : EidosValue(EidosValueType::kValueString, false), values_(p_stringvec) +EidosValue_String::EidosValue_String(const std::vector &p_stringvec) : EidosValue(EidosValueType::kValueString), values_(p_stringvec) { } -EidosValue_String::EidosValue_String(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueString, false) +EidosValue_String::EidosValue_String(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueString) { for (const auto &init_item : p_init_list) values_.emplace_back(init_item); } -EidosValue_String::EidosValue_String(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueString, false) +EidosValue_String::EidosValue_String(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueString) { for (const auto &init_item : p_init_list) values_.emplace_back(init_item); @@ -1314,7 +1314,7 @@ void EidosValue_String::Sort(bool p_ascending) #pragma mark EidosValue_Int #pragma mark - -EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValue(EidosValueType::kValueInt, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValue(EidosValueType::kValueInt), values_(&singleton_value_), count_(0), capacity_(1) { size_t count = p_intvec.size(); const int16_t *values = p_intvec.data(); @@ -1325,7 +1325,7 @@ EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValu set_int_no_check(values[index], index); } -EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValue(EidosValueType::kValueInt, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValue(EidosValueType::kValueInt), values_(&singleton_value_), count_(0), capacity_(1) { size_t count = p_intvec.size(); const int32_t *values = p_intvec.data(); @@ -1336,7 +1336,7 @@ EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValu set_int_no_check(values[index], index); } -EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValue(EidosValueType::kValueInt, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValue(EidosValueType::kValueInt), values_(&singleton_value_), count_(0), capacity_(1) { size_t count = p_intvec.size(); const int64_t *values = p_intvec.data(); @@ -1347,7 +1347,7 @@ EidosValue_Int::EidosValue_Int(const std::vector &p_intvec) : EidosValu set_int_no_check(values[index], index); } -EidosValue_Int::EidosValue_Int(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueInt, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Int::EidosValue_Int(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueInt), values_(&singleton_value_), count_(0), capacity_(1) { reserve(p_init_list.size()); @@ -1355,7 +1355,7 @@ EidosValue_Int::EidosValue_Int(std::initializer_list p_init_list) : Eid push_int_no_check(init_item); } -EidosValue_Int::EidosValue_Int(const int64_t *p_values, size_t p_count) : EidosValue(EidosValueType::kValueInt, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Int::EidosValue_Int(const int64_t *p_values, size_t p_count) : EidosValue(EidosValueType::kValueInt), values_(&singleton_value_), count_(0), capacity_(1) { resize_no_initialize(p_count); @@ -1536,7 +1536,7 @@ void EidosValue_Int::erase_index(size_t p_index) #pragma mark EidosValue_Float #pragma mark - -EidosValue_Float::EidosValue_Float(const std::vector &p_doublevec) : EidosValue(EidosValueType::kValueFloat, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Float::EidosValue_Float(const std::vector &p_doublevec) : EidosValue(EidosValueType::kValueFloat), values_(&singleton_value_), count_(0), capacity_(1) { size_t count = p_doublevec.size(); const double *values = p_doublevec.data(); @@ -1547,7 +1547,7 @@ EidosValue_Float::EidosValue_Float(const std::vector &p_doublevec) : Eid set_float_no_check(values[index], index); } -EidosValue_Float::EidosValue_Float(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueFloat, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Float::EidosValue_Float(std::initializer_list p_init_list) : EidosValue(EidosValueType::kValueFloat), values_(&singleton_value_), count_(0), capacity_(1) { reserve(p_init_list.size()); @@ -1555,7 +1555,7 @@ EidosValue_Float::EidosValue_Float(std::initializer_list p_init_list) : push_float_no_check(init_item); } -EidosValue_Float::EidosValue_Float(const double *p_values, size_t p_count) : EidosValue(EidosValueType::kValueFloat, false), values_(&singleton_value_), count_(0), capacity_(1) +EidosValue_Float::EidosValue_Float(const double *p_values, size_t p_count) : EidosValue(EidosValueType::kValueFloat), values_(&singleton_value_), count_(0), capacity_(1) { resize_no_initialize(p_count); @@ -1756,7 +1756,7 @@ void EidosValue_Float::erase_index(size_t p_index) // See comments on EidosValue_Object::EidosValue_Object() below. Note this is shared by all species. std::vector gEidosValue_Object_Mutation_Registry; -EidosValue_Object::EidosValue_Object(const EidosClass *p_class) : EidosValue(EidosValueType::kValueObject, false), +EidosValue_Object::EidosValue_Object(const EidosClass *p_class) : EidosValue(EidosValueType::kValueObject), class_(p_class), values_(&singleton_value_), count_(0), capacity_(1) { class_uses_retain_release_ = (class_ == gEidosObject_Class ? true : class_->UsesRetainRelease()); diff --git a/eidos/eidos_value.h b/eidos/eidos_value.h index a8d5594f..cbfc0ac6 100644 --- a/eidos/eidos_value.h +++ b/eidos/eidos_value.h @@ -182,7 +182,6 @@ class EidosValue const EidosValueType cached_type_; // allows Type() to be an inline function; cached at construction (uint8_t) unsigned int constant_ : 1; // if set, this EidosValue is a constant and cannot be modified unsigned int invisible_ : 1; // as in R; if true, the value will not normally be printed to the console - unsigned int is_singleton_ : 1; // allows Count() and IsSingleton() to be inline; cached at construction unsigned int registered_for_patching_ : 1; // used by EidosValue_Object, otherwise UNINITIALIZED; declared here for reasons of memory packing unsigned int class_uses_retain_release_ : 1; // used by EidosValue_Object, otherwise UNINITIALIZED; cached from UsesRetainRelease() of class_; true until class_ is set @@ -191,15 +190,13 @@ class EidosValue virtual void _CopyDimensionsFromValue(const EidosValue *p_value); // do not call directly; called by CopyDimensionsFromValue() void PrintMatrixFromIndex(int64_t p_ncol, int64_t p_nrow, int64_t p_start_index, std::ostream &p_ostream, const std::string &p_indent = std::string()) const; - virtual int Count_Virtual(void) const = 0; // the number of values in the vector - public: EidosValue(const EidosValue &p_original) = delete; // no copy-construct EidosValue& operator=(const EidosValue&) = delete; // no copying - EidosValue(void) = delete; // no null constructor - EidosValue(EidosValueType p_value_type, bool p_singleton); // must construct with a type identifier and singleton flag, which will be cached + EidosValue(void) = delete; // no null constructor + EidosValue(EidosValueType p_value_type); // must construct with a type identifier, which will be cached virtual ~EidosValue(void); // methods that raise due to various causes, used to avoid duplication and allow efficient inlining @@ -211,13 +208,12 @@ class EidosValue // basic methods inline __attribute__((always_inline)) EidosValueType Type(void) const { return cached_type_; } // the type of the vector, cached at construction - inline __attribute__((always_inline)) bool IsSingleton(void) const { return is_singleton_; } // true is the subclass is a singleton subclass (not just if Count()==1) - inline __attribute__((always_inline)) int Count(void) const { return (is_singleton_ ? 1 : Count_Virtual()); } // avoid the virtual function call for singletons // constness; note that the internal state of object elements is NOT const, just the EidosValue containing the object elements inline __attribute__((always_inline)) void MarkAsConstant(void) { constant_ = true; } inline __attribute__((always_inline)) bool IsConstant(void) const { return constant_; } + virtual int Count(void) const = 0; // the only real casualty of removing the singleton/vector distinction: this is now a virtual function virtual const std::string &ElementType(void) const = 0; // the type of the elements contained by the vector void Print(std::ostream &p_ostream, const std::string &p_indent = std::string()) const; // standard printing; same as operator<< void PrintStructure(std::ostream &p_ostream, int max_values) const; // print structure; no newline @@ -386,16 +382,14 @@ class EidosValue_VOID final : public EidosValue private: typedef EidosValue super; -protected: - virtual int Count_Virtual(void) const override { return 0; } - public: EidosValue_VOID(const EidosValue_VOID &p_original) = delete; // no copy-construct EidosValue_VOID& operator=(const EidosValue_VOID&) = delete; // no copying - inline EidosValue_VOID(void) : EidosValue(EidosValueType::kValueVOID, false) { } + inline EidosValue_VOID(void) : EidosValue(EidosValueType::kValueVOID) { } inline virtual ~EidosValue_VOID(void) override { } + virtual int Count(void) const override { return 0; } virtual const std::string &ElementType(void) const override; virtual void PrintValueAtIndex(const int p_idx, std::ostream &p_ostream) const override; virtual nlohmann::json JSONRepresentation(void) const override; @@ -424,16 +418,14 @@ class EidosValue_NULL final : public EidosValue private: typedef EidosValue super; -protected: - virtual int Count_Virtual(void) const override { return 0; } - public: EidosValue_NULL(const EidosValue_NULL &p_original) = delete; // no copy-construct EidosValue_NULL& operator=(const EidosValue_NULL&) = delete; // no copying - inline EidosValue_NULL(void) : EidosValue(EidosValueType::kValueNULL, false) { } + inline EidosValue_NULL(void) : EidosValue(EidosValueType::kValueNULL) { } inline virtual ~EidosValue_NULL(void) override { } + virtual int Count(void) const override { return 0; } virtual const std::string &ElementType(void) const override; virtual void PrintValueAtIndex(const int p_idx, std::ostream &p_ostream) const override; virtual nlohmann::json JSONRepresentation(void) const override; @@ -473,18 +465,17 @@ class EidosValue_Logical final : public EidosValue // protected to encourage use of gStaticEidosValue_LogicalT / gStaticEidosValue_LogicalF explicit EidosValue_Logical(eidos_logical_t p_logical1); - virtual int Count_Virtual(void) const override { return (int)count_; } - public: EidosValue_Logical(const EidosValue_Logical &p_original) = delete; // no copy-construct EidosValue_Logical& operator=(const EidosValue_Logical&) = delete; // no copying - inline EidosValue_Logical(void) : EidosValue(EidosValueType::kValueLogical, false) { } + inline EidosValue_Logical(void) : EidosValue(EidosValueType::kValueLogical) { } explicit EidosValue_Logical(const std::vector &p_logicalvec); explicit EidosValue_Logical(std::initializer_list p_init_list); explicit EidosValue_Logical(const eidos_logical_t *p_values, size_t p_count); inline virtual ~EidosValue_Logical(void) override { free(values_); } + virtual int Count(void) const override { return (int)count_; } virtual const std::string &ElementType(void) const override; virtual void PrintValueAtIndex(const int p_idx, std::ostream &p_ostream) const override; virtual nlohmann::json JSONRepresentation(void) const override; @@ -565,13 +556,11 @@ class EidosValue_String final : public EidosValue inline void UncacheScript(void) { if (cached_script_) { delete cached_script_; cached_script_ = nullptr; } } - virtual int Count_Virtual(void) const override { return (int)values_.size(); } - public: EidosValue_String(const EidosValue_String &p_original) = delete; // no copy-construct EidosValue_String& operator=(const EidosValue_String&) = delete; // no copying - inline EidosValue_String(void) : EidosValue(EidosValueType::kValueString, false) { } - explicit EidosValue_String(const std::string &p_string1) : EidosValue(EidosValueType::kValueString, false), values_({p_string1}) { } + inline EidosValue_String(void) : EidosValue(EidosValueType::kValueString) { } + explicit EidosValue_String(const std::string &p_string1) : EidosValue(EidosValueType::kValueString), values_({p_string1}) { } explicit EidosValue_String(const std::vector &p_stringvec); explicit EidosValue_String(std::initializer_list p_init_list); explicit EidosValue_String(std::initializer_list p_init_list); @@ -581,6 +570,7 @@ class EidosValue_String final : public EidosValue virtual std::string *StringData_Mutable(void) override { WILL_MODIFY(this); UncacheScript(); return values_.data(); } std::vector &StringVectorData(void) { WILL_MODIFY(this); UncacheScript(); return values_; } // to get the std::vector for direct modification + virtual int Count(void) const override { return (int)values_.size(); } virtual const std::string &ElementType(void) const override; virtual EidosValue_SP NewMatchingType(void) const override; virtual void PrintValueAtIndex(const int p_idx, std::ostream &p_ostream) const override; @@ -629,14 +619,12 @@ class EidosValue_Int final : public EidosValue int64_t *values_ = nullptr; size_t count_, capacity_; - virtual int Count_Virtual(void) const override { return (int)count_; } - public: EidosValue_Int(const EidosValue_Int &p_original) = delete; // no copy-construct EidosValue_Int& operator=(const EidosValue_Int&) = delete; // no copying - explicit inline EidosValue_Int(void) : EidosValue(EidosValueType::kValueInt, false), values_(&singleton_value_), count_(0), capacity_(1) { } - explicit inline EidosValue_Int(int64_t p_int1) : EidosValue(EidosValueType::kValueInt, false), singleton_value_(p_int1), values_(&singleton_value_), count_(1), capacity_(1) { } + explicit inline EidosValue_Int(void) : EidosValue(EidosValueType::kValueInt), values_(&singleton_value_), count_(0), capacity_(1) { } + explicit inline EidosValue_Int(int64_t p_int1) : EidosValue(EidosValueType::kValueInt), singleton_value_(p_int1), values_(&singleton_value_), count_(1), capacity_(1) { } explicit EidosValue_Int(const std::vector &p_intvec); explicit EidosValue_Int(const std::vector &p_intvec); explicit EidosValue_Int(const std::vector &p_intvec); @@ -647,6 +635,7 @@ class EidosValue_Int final : public EidosValue virtual const int64_t *IntData(void) const override { return values_; } virtual int64_t *IntData_Mutable(void) override { WILL_MODIFY(this); return values_; } + virtual int Count(void) const override { return (int)count_; } virtual const std::string &ElementType(void) const override; virtual EidosValue_SP NewMatchingType(void) const override; virtual void PrintValueAtIndex(const int p_idx, std::ostream &p_ostream) const override; @@ -739,14 +728,12 @@ class EidosValue_Float final : public EidosValue double *values_; size_t count_, capacity_; - virtual int Count_Virtual(void) const override { return (int)count_; } - public: EidosValue_Float(const EidosValue_Float &p_original) = delete; // no copy-construct EidosValue_Float& operator=(const EidosValue_Float&) = delete; // no copying - explicit inline EidosValue_Float(void) : EidosValue(EidosValueType::kValueFloat, false), values_(&singleton_value_), count_(0), capacity_(1) { } - explicit inline EidosValue_Float(double p_float1) : EidosValue(EidosValueType::kValueFloat, false), singleton_value_(p_float1), values_(&singleton_value_), count_(1), capacity_(1) { } + explicit inline EidosValue_Float(void) : EidosValue(EidosValueType::kValueFloat), values_(&singleton_value_), count_(0), capacity_(1) { } + explicit inline EidosValue_Float(double p_float1) : EidosValue(EidosValueType::kValueFloat), singleton_value_(p_float1), values_(&singleton_value_), count_(1), capacity_(1) { } explicit EidosValue_Float(const std::vector &p_doublevec); explicit EidosValue_Float(std::initializer_list p_init_list); explicit EidosValue_Float(const double *p_values, size_t p_count); @@ -755,6 +742,7 @@ class EidosValue_Float final : public EidosValue virtual const double *FloatData(void) const override { return values_; } virtual double *FloatData_Mutable(void) override { WILL_MODIFY(this); return values_; } + virtual int Count(void) const override { return (int)count_; } virtual const std::string &ElementType(void) const override; virtual EidosValue_SP NewMatchingType(void) const override; virtual void PrintValueAtIndex(const int p_idx, std::ostream &p_ostream) const override; @@ -862,8 +850,6 @@ class EidosValue_Object final : public EidosValue //unsigned int registered_for_patching_ : 1; // for mutation pointer patching; see EidosValue_Object::EidosValue_Object() //unsigned int class_uses_retain_release_ : 1; // cached from UsesRetainRelease() of class_; true until class_ is set - virtual int Count_Virtual(void) const override { return (int)count_; } - // check the type of a new element being added to an EidosValue_Object, and update class_uses_retain_release_ inline __attribute__((always_inline)) void DeclareClassFromElement(const EidosObject *p_element, bool p_undeclared_is_error = false) { @@ -908,6 +894,7 @@ class EidosValue_Object final : public EidosValue inline __attribute__((always_inline)) const EidosClass *Class(void) const { return class_; } inline __attribute__((always_inline)) bool UsesRetainRelease(void) const { return class_uses_retain_release_; } + virtual int Count(void) const override { return (int)count_; } virtual const std::string &ElementType(void) const override; virtual EidosValue_SP NewMatchingType(void) const override; virtual void PrintValueAtIndex(const int p_idx, std::ostream &p_ostream) const override;