]> git.saurik.com Git - apple/icu.git/blob - icuSources/common/simplepatternformatter.h
ICU-551.24.tar.gz
[apple/icu.git] / icuSources / common / simplepatternformatter.h
1 /*
2 ******************************************************************************
3 * Copyright (C) 2014, International Business Machines
4 * Corporation and others. All Rights Reserved.
5 ******************************************************************************
6 * simplepatternformatter.h
7 */
8
9 #ifndef __SIMPLEPATTERNFORMATTER_H__
10 #define __SIMPLEPATTERNFORMATTER_H__
11
12 #define EXPECTED_PLACEHOLDER_COUNT 3
13
14 #include "cmemory.h"
15 #include "unicode/utypes.h"
16 #include "unicode/unistr.h"
17
18 U_NAMESPACE_BEGIN
19
20 class SimplePatternFormatterPlaceholderValues;
21
22 struct PlaceholderInfo {
23 int32_t id;
24 int32_t offset;
25 };
26
27 /**
28 * Compiled version of a pattern string such as "{1} was born in {0}".
29 * <p>
30 * Using SimplePatternFormatter is both faster and safer than adhoc replacement.
31 * They are faster because they are precompiled; they are safer because they
32 * account for curly braces escaped by apostrophe (').
33 *
34 * Placeholders are of the form \{[0-9]+\}. If a curly brace is preceded
35 * by a single quote, it becomes a curly brace instead of the start of a
36 * placeholder. Two single quotes resolve to one single quote.
37 * <p>
38 * Example:
39 * <pre>
40 * SimplePatternFormatter fmt("{1} '{born} in {0}");
41 * UnicodeString result;
42 * UErrorCode status = U_ZERO_ERROR;
43 * // Evaluates to: "paul {born} in england"
44 * fmt.format("england", "paul", result, status);
45 * </pre>
46 */
47 class U_COMMON_API SimplePatternFormatter : public UMemory {
48 public:
49 /**
50 * Default constructor
51 */
52 SimplePatternFormatter();
53
54 /**
55 * Construct from a pattern. Will never fail if pattern has three or
56 * fewer placeholders in it.
57 */
58 explicit SimplePatternFormatter(const UnicodeString& pattern);
59
60 /**
61 * Copy constructor.
62 */
63 SimplePatternFormatter(const SimplePatternFormatter& other);
64
65 /**
66 * Assignment operator
67 */
68 SimplePatternFormatter &operator=(const SimplePatternFormatter& other);
69
70 /**
71 * Destructor.
72 */
73 ~SimplePatternFormatter();
74
75 /**
76 * Compiles pattern and makes this object represent pattern.
77 *
78 * Returns TRUE on success; FALSE on failure. Will not fail if
79 * there are three or fewer placeholders in pattern. May fail with
80 * U_MEMORY_ALLOCATION_ERROR if there are more than three placeholders.
81 */
82 UBool compile(const UnicodeString &pattern, UErrorCode &status);
83
84 /**
85 * Returns (maxPlaceholderId + 1). For example
86 * <code>SimplePatternFormatter("{0} {2}").getPlaceholderCount()
87 * evaluates to 3.
88 * Callers use this function to find out how many values this object
89 * expects when formatting.
90 */
91 int32_t getPlaceholderCount() const {
92 return placeholderCount;
93 }
94
95 /**
96 * Returns this pattern with none of the placeholders.
97 */
98 const UnicodeString &getPatternWithNoPlaceholders() const {
99 return noPlaceholders;
100 }
101
102 /**
103 * Formats given value. arg0 cannot be appendTo.
104 */
105 UnicodeString &format(
106 const UnicodeString &args0,
107 UnicodeString &appendTo,
108 UErrorCode &status) const;
109
110 /**
111 * Formats given values. Neither arg0 nor arg1 can be appendTo.
112 */
113 UnicodeString &format(
114 const UnicodeString &args0,
115 const UnicodeString &args1,
116 UnicodeString &appendTo,
117 UErrorCode &status) const;
118
119 /**
120 * Formats given values. Neither arg0, arg1, nor arg2 can be appendTo.
121 */
122 UnicodeString &format(
123 const UnicodeString &args0,
124 const UnicodeString &args1,
125 const UnicodeString &args2,
126 UnicodeString &appendTo,
127 UErrorCode &status) const;
128
129 /**
130 * Formats given values.
131 *
132 * The caller retains ownership of all pointers.
133 * @param placeholderValues 1st one corresponds to {0}; 2nd to {1};
134 * 3rd to {2} etc. If any of these point to appendTo, this method
135 * sets status to U_ILLEGAL_ARGUMENT_ERROR.
136 * @param placeholderValueCount the number of placeholder values
137 * must be at least large enough to provide values for all placeholders
138 * in this object. Otherwise status set to U_ILLEGAL_ARGUMENT_ERROR.
139 * @param appendTo resulting string appended here.
140 * @param offsetArray The offset of each placeholder value in appendTo
141 * stored here. The first value gets the offset of the value for {0};
142 * the 2nd for {1}; the 3rd for {2} etc. -1 means that the corresponding
143 * placeholder does not exist in this object. If caller is not
144 * interested in offsets, it may pass NULL and 0 for the length.
145 * @param offsetArrayLength the size of offsetArray. If less than
146 * placeholderValueCount only the first offsets get recorded. If
147 * greater than placeholderValueCount, then extra values in offset
148 * array are set to -1.
149 * @param status any error stored here.
150 */
151 UnicodeString &formatAndAppend(
152 const UnicodeString * const *placeholderValues,
153 int32_t placeholderValueCount,
154 UnicodeString &appendTo,
155 int32_t *offsetArray,
156 int32_t offsetArrayLength,
157 UErrorCode &status) const;
158
159 /**
160 * Formats given values.
161 *
162 * The caller retains ownership of all pointers.
163 * @param placeholderValues 1st one corresponds to {0}; 2nd to {1};
164 * 3rd to {2} etc. May include pointer to result in which case
165 * the previous value of result is used for the corresponding
166 * placeholder.
167 * @param placeholderValueCount the number of placeholder values
168 * must be at least large enough to provide values for all placeholders
169 * in this object. Otherwise status set to U_ILLEGAL_ARGUMENT_ERROR.
170 * @param result resulting string stored here overwriting any previous
171 * value.
172 * @param offsetArray The offset of each placeholder value in result
173 * stored here. The first value gets the offset of the value for {0};
174 * the 2nd for {1}; the 3rd for {2} etc. -1 means that the corresponding
175 * placeholder does not exist in this object. If caller is not
176 * interested in offsets, it may pass NULL and 0 for the length.
177 * @param offsetArrayLength the size of offsetArray. If less than
178 * placeholderValueCount only the first offsets get recorded. If
179 * greater than placeholderValueCount, then extra values in offset
180 * array are set to -1.
181 * @param status any error stored here.
182 */
183 UnicodeString &formatAndReplace(
184 const UnicodeString * const *placeholderValues,
185 int32_t placeholderValueCount,
186 UnicodeString &result,
187 int32_t *offsetArray,
188 int32_t offsetArrayLength,
189 UErrorCode &status) const;
190 private:
191 UnicodeString noPlaceholders;
192 MaybeStackArray<PlaceholderInfo, 3> placeholders;
193 int32_t placeholderSize;
194 int32_t placeholderCount;
195 UBool firstPlaceholderReused;
196
197 // A Placeholder value that is the same as appendTo is treated as the
198 // empty string.
199 UnicodeString &formatAndAppend(
200 const SimplePatternFormatterPlaceholderValues &placeholderValues,
201 UnicodeString &appendTo,
202 int32_t *offsetArray,
203 int32_t offsetArrayLength) const;
204
205 // Returns the placeholder at the beginning of this pattern
206 // (e.g 3 for placeholder {3}). Returns -1 if the beginning of pattern
207 // is text or if the placeholder at the beginning of this pattern
208 // is used again in the middle of the pattern.
209 int32_t getUniquePlaceholderAtStart() const;
210
211 // ensureCapacity ensures that the capacity of the placeholders array
212 // is desiredCapacity. If ensureCapacity must resize the placeholders
213 // array, the first placeholderSize elements stay in the array. Note
214 // that ensureCapcity NEVER changes the value of placeholderSize only
215 // the capacity of the placeholders array.
216 // If there is no memory allocation error when resizing, this
217 // function returns desiredCapacity. If there is a memory allocation
218 // error, this function leaves the placeholders array unchanged and
219 // returns the smaller, old capacity. ensureCapacity resizes only if
220 // the current capacity of placeholders array is less than desiredCapacity.
221 // Otherwise, it leaves the placeholders array unchanged. If caller
222 // specifies an allocation size, then it must be at least as large as
223 // desiredCapacity. In that case, if ensureCapacity resizes, it will
224 // allocate allocationSize spots instead of desiredCapacity spots in
225 // the array. If caller is calling ensureCapacity in a loop while adding
226 // elements, it is recommended that it use an allocationSize of
227 // approximately twice desiredCapacity to avoid memory allocation with
228 // every call to ensureCapacity.
229 int32_t ensureCapacity(int32_t desiredCapacity, int32_t allocationSize=0);
230
231 // Records the offset of an individual placeholder in the noPlaceholders
232 // string.
233 UBool addPlaceholder(int32_t id, int32_t offset);
234 };
235
236 U_NAMESPACE_END
237
238 #endif