• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // © 2017 and later: Unicode, Inc. and others.
2 // License & terms of use: http://www.unicode.org/copyright.html
3 
4 #include "unicode/utypes.h"
5 
6 #if !UCONFIG_NO_FORMATTING
7 
8 #include "number_decimfmtprops.h"
9 #include "umutex.h"
10 
11 using namespace icu;
12 using namespace icu::number;
13 using namespace icu::number::impl;
14 
15 
16 namespace {
17 
18 alignas(DecimalFormatProperties)
19 char kRawDefaultProperties[sizeof(DecimalFormatProperties)];
20 
21 icu::UInitOnce gDefaultPropertiesInitOnce {};
22 
initDefaultProperties(UErrorCode &)23 void U_CALLCONV initDefaultProperties(UErrorCode&) {
24     // can't fail, uses placement new into statically allocated space.
25     new(kRawDefaultProperties) DecimalFormatProperties(); // set to the default instance
26 }
27 
28 }
29 
30 
DecimalFormatProperties()31 DecimalFormatProperties::DecimalFormatProperties() {
32     clear();
33 }
34 
clear()35 void DecimalFormatProperties::clear() {
36     compactStyle.nullify();
37     currency.nullify();
38     currencyPluralInfo.fPtr.adoptInstead(nullptr);
39     currencyUsage.nullify();
40     decimalPatternMatchRequired = false;
41     decimalSeparatorAlwaysShown = false;
42     exponentSignAlwaysShown = false;
43     currencyAsDecimal = false;
44     formatFailIfMoreThanMaxDigits = false;
45     formatWidth = -1;
46     groupingSize = -1;
47     groupingUsed = true;
48     magnitudeMultiplier = 0;
49     maximumFractionDigits = -1;
50     maximumIntegerDigits = -1;
51     maximumSignificantDigits = -1;
52     minimumExponentDigits = -1;
53     minimumFractionDigits = -1;
54     minimumGroupingDigits = -1;
55     minimumIntegerDigits = -1;
56     minimumSignificantDigits = -1;
57     multiplier = 1;
58     multiplierScale = 0;
59     negativePrefix.setToBogus();
60     negativePrefixPattern.setToBogus();
61     negativeSuffix.setToBogus();
62     negativeSuffixPattern.setToBogus();
63     padPosition.nullify();
64     padString.setToBogus();
65     parseCaseSensitive = false;
66     parseIntegerOnly = false;
67     parseMode.nullify();
68     parseNoExponent = false;
69     parseToBigDecimal = false;
70     parseAllInput = UNUM_MAYBE;
71     positivePrefix.setToBogus();
72     positivePrefixPattern.setToBogus();
73     positiveSuffix.setToBogus();
74     positiveSuffixPattern.setToBogus();
75     roundingIncrement = 0.0;
76     roundingMode.nullify();
77     secondaryGroupingSize = -1;
78     signAlwaysShown = false;
79 }
80 
81 bool
_equals(const DecimalFormatProperties & other,bool ignoreForFastFormat) const82 DecimalFormatProperties::_equals(const DecimalFormatProperties& other, bool ignoreForFastFormat) const {
83     bool eq = true;
84 
85     // Properties that must be equal both normally and for fast-path formatting
86     eq = eq && compactStyle == other.compactStyle;
87     eq = eq && currency == other.currency;
88     eq = eq && currencyPluralInfo.fPtr.getAlias() == other.currencyPluralInfo.fPtr.getAlias();
89     eq = eq && currencyUsage == other.currencyUsage;
90     eq = eq && decimalSeparatorAlwaysShown == other.decimalSeparatorAlwaysShown;
91     eq = eq && exponentSignAlwaysShown == other.exponentSignAlwaysShown;
92     eq = eq && currencyAsDecimal == other.currencyAsDecimal;
93     eq = eq && formatFailIfMoreThanMaxDigits == other.formatFailIfMoreThanMaxDigits;
94     eq = eq && formatWidth == other.formatWidth;
95     eq = eq && magnitudeMultiplier == other.magnitudeMultiplier;
96     eq = eq && maximumSignificantDigits == other.maximumSignificantDigits;
97     eq = eq && minimumExponentDigits == other.minimumExponentDigits;
98     eq = eq && minimumGroupingDigits == other.minimumGroupingDigits;
99     eq = eq && minimumSignificantDigits == other.minimumSignificantDigits;
100     eq = eq && multiplier == other.multiplier;
101     eq = eq && multiplierScale == other.multiplierScale;
102     eq = eq && negativePrefix == other.negativePrefix;
103     eq = eq && negativeSuffix == other.negativeSuffix;
104     eq = eq && padPosition == other.padPosition;
105     eq = eq && padString == other.padString;
106     eq = eq && positivePrefix == other.positivePrefix;
107     eq = eq && positiveSuffix == other.positiveSuffix;
108     eq = eq && roundingIncrement == other.roundingIncrement;
109     eq = eq && roundingMode == other.roundingMode;
110     eq = eq && secondaryGroupingSize == other.secondaryGroupingSize;
111     eq = eq && signAlwaysShown == other.signAlwaysShown;
112 
113     if (ignoreForFastFormat) {
114         return eq;
115     }
116 
117     // Properties ignored by fast-path formatting
118     // Formatting (special handling required):
119     eq = eq && groupingSize == other.groupingSize;
120     eq = eq && groupingUsed == other.groupingUsed;
121     eq = eq && minimumFractionDigits == other.minimumFractionDigits;
122     eq = eq && maximumFractionDigits == other.maximumFractionDigits;
123     eq = eq && maximumIntegerDigits == other.maximumIntegerDigits;
124     eq = eq && minimumIntegerDigits == other.minimumIntegerDigits;
125     eq = eq && negativePrefixPattern == other.negativePrefixPattern;
126     eq = eq && negativeSuffixPattern == other.negativeSuffixPattern;
127     eq = eq && positivePrefixPattern == other.positivePrefixPattern;
128     eq = eq && positiveSuffixPattern == other.positiveSuffixPattern;
129 
130     // Parsing (always safe to ignore):
131     eq = eq && decimalPatternMatchRequired == other.decimalPatternMatchRequired;
132     eq = eq && parseCaseSensitive == other.parseCaseSensitive;
133     eq = eq && parseIntegerOnly == other.parseIntegerOnly;
134     eq = eq && parseMode == other.parseMode;
135     eq = eq && parseNoExponent == other.parseNoExponent;
136     eq = eq && parseToBigDecimal == other.parseToBigDecimal;
137     eq = eq && parseAllInput == other.parseAllInput;
138 
139     return eq;
140 }
141 
equalsDefaultExceptFastFormat() const142 bool DecimalFormatProperties::equalsDefaultExceptFastFormat() const {
143     UErrorCode localStatus = U_ZERO_ERROR;
144     umtx_initOnce(gDefaultPropertiesInitOnce, &initDefaultProperties, localStatus);
145     return _equals(*reinterpret_cast<DecimalFormatProperties*>(kRawDefaultProperties), true);
146 }
147 
getDefault()148 const DecimalFormatProperties& DecimalFormatProperties::getDefault() {
149     UErrorCode localStatus = U_ZERO_ERROR;
150     umtx_initOnce(gDefaultPropertiesInitOnce, &initDefaultProperties, localStatus);
151     return *reinterpret_cast<const DecimalFormatProperties*>(kRawDefaultProperties);
152 }
153 
154 #endif /* #if !UCONFIG_NO_FORMATTING */
155