// bdldfp_decimalformatconfig.h -*-C++-*- #ifndef INCLUDED_BDLDFP_DECIMALFORMATCONFIG #define INCLUDED_BDLDFP_DECIMALFORMATCONFIG #include <bsls_ident.h> BSLS_IDENT("$Id$") //@PURPOSE: Provide an attribute class to configure decimal formatting. // //@CLASSES: // bdldfp::DecimalFormatConfig: configuration for formatting functions // //@SEE_ALSO: bdldfp_decimalutil // //@DESCRIPTION: This component provides a single, simply constrained // (value-semantic) attribute class, 'bdldfp::DecimalFormatConfig', that is // used to configure various aspects of decimal value formatting. // ///Attributes ///---------- //.. // Name Type Default Simple Constraints // --------- ------ --------------- ------------------ // style Style e_NATURAL none // precision int 0 >= 0 // sign Sign e_NEGATIVE_ONLY none // infinity string "inf" none // nan string "nan" none // snan string "snan" none // point char '.' none // exponent char 'e' none // showpoint bool false none // expwidth int 2 >= 1, <= 4 //.. //: o 'style': control how the decimal number is written. If 'style' is //: 'e_SCIENTIFIC', the number is written as its sign, then a single digit, //: then the decimal point, then 'precision' digits, then the 'exponent' //: character, then a '-' or '+', then an exponent with no leading zeroes //: (with a zero exponent written as '0'). If 'style' is 'e_FIXED', the //: number is written as its sign, then one or more digits, then the decimal //: point, then 'precision' digits. If the 'precision' value equals '0' then //: 'precision' digits and the decimal point are not written. If 'style' is //: 'e_NATURAL', the number is written according to the description of //: 'to-scientific-string' found in //: http://speleotrove.com/decimal/decarith.pdf (and no other specified //: formatting values are used, including precision). //: //: o 'precision': control how many digits are written after the decimal point //: if the decimal number is rendered in 'e_FIXED' and 'e_SCIENTIFIC' //: formats. Note that 'precision' attribute is ignored in 'e_NATURAL' //: format. //: //: o 'sign': control how the sign is output. If a decimal value has its sign //: bit set, a '-' is always written. Otherwise, if 'sign' is //: 'e_NEGATIVE_ONLY', no sign is written. If it is 'e_ALWAYS', a '+' is //: written. //: //: o 'infinity': specify a string to output infinity value. //: //: o 'nan': specify a string to output NaN value. //: //: o 'snan': specify a string to output signaling NaN value. //: //: o 'point': specify the character to use for decimal points. //: //: o 'exponent': specify the character to use for exponent when 'style' is //: 'e_SCIENTIFIC' or 'e_NATURAL'. //: //: o 'showpoint': specify whether a decimal point is always displayed. //: //: o 'expwidth': control the minimum number of digits used to write the //: exponent. #include <bsl_cstring.h> #include <bsls_assert.h> namespace BloombergLP { namespace bdldfp { // ========================= // class DecimalFormatConfig // ========================= class DecimalFormatConfig { // This attribute class characterizes how to configure certain behavior of // 'bdldfp::DecimalUtil::format' functions. public: // TYPES enum Sign { e_NEGATIVE_ONLY, // no sign output when sign bit is not set e_ALWAYS // output '+' when sign bit is not set }; enum Style { e_SCIENTIFIC, // output number in scientific notation e_FIXED, // output number in fixed-format e_NATURAL // output number in "to-scientific-string" format // described in // {http://speleotrove.com/decimal/decarith.pdf} }; private: // DATA int d_precision; // precision (number of digits after point) Style d_style; // formatting style Sign d_sign; // sign character const char *d_infinityText; // infinity representation const char *d_nanText; // NaN representation const char *d_sNanText; // signaling NaN representation char d_decimalPoint; // decimal point character char d_exponent; // exponent character bool d_showpoint; // always show decimal int d_expWidth; // minimum digits in exponent // FRIENDS friend bool operator==(const DecimalFormatConfig&, const DecimalFormatConfig&); friend bool operator!=(const DecimalFormatConfig&, const DecimalFormatConfig&); public: // CREATORS DecimalFormatConfig(); // Create an object of this class having the (default) attribute // values: //.. // precision == 0 // style == e_NATURAL // sign == e_NEGATIVE_ONLY // infinity == "inf" // nan == "nan" // snan == "snan" // point == '.' // exponent == 'e' // expwidth == 2 // showpoint == false //.. explicit DecimalFormatConfig(int precision, Style style = e_NATURAL, Sign sign = e_NEGATIVE_ONLY, const char *infinity = "inf", const char *nan = "nan", const char *snan = "snan", char point = '.', char exponent = 'e', bool showpoint = false, int expWidth = 2); // Create an object of this class having the specified 'precision' to // control how many digits are written after a decimal point. The // behavior is undefined if 'precision' is negative. Optionally // specify 'style' to control how the number is written. If it is not // specified, 'e_NATURAL' is used. Optionally specify 'sign' to // control how the sign is output. If is not specified, // 'e_NEGATIVE_ONLY' is used. Optionally specify 'infinity' as a // string to output infinity value. If it is not specified, "inf" is // used. Optionally specify 'nan' as a string to output NaN value. If // it is not specified, "nan" is used. Optionally specify 'snan' as a // string to output signaling NaN value. If it is not specified, // "snan" is used. The behavior is undefined unless the pointers to // 'infinity', 'nan' and 'snan' remain valid for the lifetime of this // object. Optionally specify 'point' as the character to use for // decimal points. If it is not specified, '.' is used. Optionally // specify 'exponent' as the character to use for exponent. If it is // not specified, 'e' is used. Optionally specify 'showpoint' to force // a decimal point to always be written. Optionally specify 'expWidth' // to force at least that many digits to be written for an exponent, up // to the number of digits in the largest supported exponent. If it is // not specified, 2 is used. The behavior is undefined unless // 'expWidth' is 1, 2, 3, or 4. See the Attributes section under // @DESCRIPTION in the component-level documentation for information on // the class attributes. // MANIPULATORS void setPrecision (int value); // Set the 'precision' attribute of this object to the specified // 'value'. Behavior is undefined if 'value' is negative. void setStyle(Style value); // Set the 'style' attribute of this object to the specified 'value'. void setSign(Sign value); // Set the 'sign' attribute of this object to the specified 'value'. void setInfinity(const char *value); // Set the 'infinity' attribute of this object to the specified // 'value'. The behavior is undefined unless the pointer to the // 'value' remains valid for the lifetime of this object. void setNan(const char *value); // Set the 'nan' attribute of this object to the specified 'value'. // The behavior is undefined unless the pointer to the 'value' remains // valid for the lifetime of this object. void setSNan(const char *value); // Set the 'snan' attribute of this object to the specified 'value'. // The behavior is undefined unless the pointer to the 'value' remains // valid for the lifetime of this object. void setDecimalPoint(char value); // Set the 'point' attribute of this object to the specified 'value'. void setExponent(char value); // Set the 'exponent' attribute of this object to the specified // 'value'. void setShowpoint(bool value); // Set the 'showpoint' attribute of this object to the specified // 'value'. void setExpWidth(int value); // Set the 'expwidth' attribute of this object to the specified // 'value'. The behavior is undefined unless 'value' is 1, 2, 3, or 4. // ACCESSORS int precision() const; // Return the number of digits of precision in the outputs. Style style() const; // Return the style of output format. Sign sign() const; // Return the sign attribute. const char *infinity() const; // Return infinity string representation. const char *nan() const; // Return NaN string representation. const char *sNan() const; // Return sNaN string representation. char decimalPoint() const; // Return point character. char exponent() const; // Return exponent character. bool showpoint() const; // Return the 'showpoint' attribute. int expWidth() const; // Return the minimum exponent width. }; // FREE OPERATORS bool operator==(const DecimalFormatConfig& lhs, const DecimalFormatConfig& rhs); // Return 'true' if the specified 'lhs' and 'rhs' objects have the same // value, and 'false' otherwise. Two 'DecimalFormatConfig' objects have // the same value if each of their attributes (respectively) have the same // value. Note that comparison of two string type attributes are done via // 'bsl::strcmp() function. bool operator!=(const DecimalFormatConfig& lhs, const DecimalFormatConfig& rhs); // Return 'true' if the specified 'lhs' and 'rhs' objects do not have the // same value, and 'false' otherwise. Two 'DecimalFormatConfig' objects // do not have the same value if any of their attributes (respectively) do // not have the same value. Note that comparison of two string type // attributes are done via 'bsl::strcmp() function. // ============================================================================ // INLINE DEFINITIONS // ============================================================================ // ------------------------- // class DecimalFormatConfig // ------------------------- // CREATORS inline DecimalFormatConfig::DecimalFormatConfig() : d_precision(0) , d_style(e_NATURAL) , d_sign(e_NEGATIVE_ONLY) , d_infinityText("inf") , d_nanText("nan") , d_sNanText("snan") , d_decimalPoint('.') , d_exponent('e') , d_showpoint(false) , d_expWidth(2) { } inline DecimalFormatConfig::DecimalFormatConfig(int precision, Style style, Sign sign, const char *infinity, const char *nan, const char *snan, char point, char exponent, bool showpoint, int expWidth) : d_precision(precision) , d_style(style) , d_sign(sign) , d_infinityText(infinity) , d_nanText(nan) , d_sNanText(snan) , d_decimalPoint(point) , d_exponent(exponent) , d_showpoint(showpoint) , d_expWidth(expWidth) { BSLS_ASSERT(precision >= 0); BSLS_ASSERT(infinity); BSLS_ASSERT(nan); BSLS_ASSERT(snan); BSLS_ASSERT(expWidth >= 1); BSLS_ASSERT(expWidth <= 4); } // MANIPULATORS inline void DecimalFormatConfig::setPrecision (int value) { BSLS_ASSERT(value >= 0); d_precision = value; } inline void DecimalFormatConfig::setStyle(Style value) { d_style = value; } inline void DecimalFormatConfig::setSign(Sign value) { d_sign = value; } inline void DecimalFormatConfig::setInfinity(const char *value) { BSLS_ASSERT(value); d_infinityText = value; } inline void DecimalFormatConfig::setNan(const char *value) { BSLS_ASSERT(value); d_nanText = value; } inline void DecimalFormatConfig::setSNan(const char *value) { BSLS_ASSERT(value); d_sNanText = value; } inline void DecimalFormatConfig::setDecimalPoint(char value) { d_decimalPoint = value; } inline void DecimalFormatConfig::setExponent(char value) { d_exponent = value; } inline void DecimalFormatConfig::setShowpoint(bool value) { d_showpoint = value; } inline void DecimalFormatConfig::setExpWidth(int value) { BSLS_ASSERT(value >= 1); BSLS_ASSERT(value <= 4); d_expWidth = value; } // ACCESSORS inline int DecimalFormatConfig::precision() const { return d_precision; } inline DecimalFormatConfig::Style DecimalFormatConfig::style() const { return d_style; } inline DecimalFormatConfig::Sign DecimalFormatConfig::sign() const { return d_sign; } inline const char *DecimalFormatConfig::infinity() const { return d_infinityText; } inline const char *DecimalFormatConfig::nan() const { return d_nanText; } inline const char *DecimalFormatConfig::sNan() const { return d_sNanText; } inline char DecimalFormatConfig::decimalPoint() const { return d_decimalPoint; } inline char DecimalFormatConfig::exponent() const { return d_exponent; } inline bool DecimalFormatConfig::showpoint() const { return d_showpoint; } inline int DecimalFormatConfig::expWidth() const { return d_expWidth; } } // close package namespace // FREE OPERATORS inline bool bdldfp::operator==(const DecimalFormatConfig& lhs, const DecimalFormatConfig& rhs) { return lhs.d_precision == rhs.d_precision && lhs.d_style == rhs.d_style && lhs.d_sign == rhs.d_sign && bsl::strcmp(lhs.d_infinityText, rhs.d_infinityText) == 0 && bsl::strcmp(lhs.d_nanText, rhs.d_nanText) == 0 && bsl::strcmp(lhs.d_sNanText, rhs.d_sNanText) == 0 && lhs.d_decimalPoint == rhs.d_decimalPoint && lhs.d_exponent == rhs.d_exponent && lhs.d_showpoint == rhs.d_showpoint && lhs.d_expWidth == rhs.d_expWidth; } inline bool bdldfp::operator!=(const DecimalFormatConfig& lhs, const DecimalFormatConfig& rhs) { return lhs.d_precision != rhs.d_precision || lhs.d_style != rhs.d_style || lhs.d_sign != rhs.d_sign || bsl::strcmp(lhs.d_infinityText, rhs.d_infinityText) || bsl::strcmp(lhs.d_nanText, rhs.d_nanText) || bsl::strcmp(lhs.d_sNanText, rhs.d_sNanText) || lhs.d_decimalPoint != rhs.d_decimalPoint || lhs.d_exponent != rhs.d_exponent || lhs.d_showpoint != rhs.d_showpoint || lhs.d_expWidth != rhs.d_expWidth; } } // close enterprise namespace #endif // ---------------------------------------------------------------------------- // Copyright 2017 Bloomberg Finance L.P. // // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. // ----------------------------- END-OF-FILE ----------------------------------